Rekursiven Algorithmus für koaleszierende / Kollabieren Liste der Daten in Bereiche
-
27-09-2019 - |
Frage
eine Liste von Daten Gegeben
12/07/2010
13/07/2010
14/07/2010
15/07/2010
12/08/2010
13/08/2010
14/08/2010
15/08/2010
19/08/2010
20/08/2010
21/08/2010
Ich suche Zeiger auf einem rekursive Pseudo-Code-Algorithmus (die ich in eine Filemaker benutzerdefinierten Funktion übersetzen kann) für eine Liste der Bereiche Herstellung, d.
12/07/2010 to 15/07/2010, 12/08/2010 to 15/08/2010, 19/08/2010 to 20/08/2010
Die Liste wird vorsortiert und dedupliziert. Ich habe versucht, sowohl von dem ersten Wert und arbeiten Sie nach vorn, und dem letzten Wert und rückwärts arbeiten, aber ich kann einfach nicht scheinen, um es an der Arbeit zu machen. Ein jener frustrierenden Tage ... Es wäre schön, wenn die Signatur so etwas wie
istCollapseDateList( dateList, separator, ellipsis )
: -)
Lösung
Die Hauptroutine würde wie folgt aussehen:
List<String> list = new ArrayList<String>();
String firstDate = dateList[0];
String lastDate = dateList[0];
String currentDate = dateList[0];
for (int i = 1; i < dateList.length(); i++) {
if (dateDiff(dateList[i], currentDate) == 1) {
lastDate = dateList[i];
} else {
list.add(firstDate + separator + lastDate);
firstDate = dateList[i];
lastDate = dateList[i];
}
currentDate = dateList[i];
}
list.add(firstDate + separator + lastDate);
Ich gehe davon aus Sie eine Funktion haben, die Ihnen sagt, wenn zwei Daten aufeinander folgend sind oder nicht.
Andere Tipps
Hier ist der rekursive Filemaker-Code, der die Arbeit erledigt. Der grundlegende Ansatz ist es, den Austausch an seinem Platz zu tun, wo notwendig, das Datum des letzten Datum (am weitesten rechts stehende Wort) in einem Wert zu berechnen. Auf diese Weise, es entscheiden kann, wann, wenn der nächste Wert zu prüfen, noch ein Teil des ersten Bereichs liegt, oder den ersten Bereich markiert, wie getan und Fokus in auf dem Rest der Werte. Hoffe, es hilft jemand anderes.
// CollapseDateList( dates, comma, dash)
Let(
countDates = ValueCount ( dates );
If (
countDates < 2 ; dates; // return the dates we've been given...
Let(
[
start_date = GetAsDate( LeftWords( GetValue ( dates ; 1 ); 1 ) );
date_1 = GetAsDate( RightWords( GetValue ( dates ; 1 ); 1 ) );
date_2 = GetAsDate( GetValue ( dates ; 2 ) );
date_3 = GetAsDate( GetValue ( dates ; 3 ) );
dv_1 = GetAsNumber( date_1 );
dv_2 = GetAsNumber( date_2 );
dv_3 = GetAsNumber( date_3 );
twoFollowsOne = (dv_2 = dv_1 + 1);
threeFollowsTwo = (dv_3 = dv_2 + 1)
];
// compare dates
Case(
// only two dates in list
countDates = 2;
if (
twoFollowsOne;
start_date & dash & date_2;
GetValue ( dates ; 1 ) & comma & date_2
);
// first three values are sequential
threeFollowsTwo and twoFollowsOne;
CollapseDateList( start_date & dash & date_3 & ¶ & RightValues( dates; countDates - 3 ); comma; dash );
// first two values are sequential only
not threeFollowsTwo and twoFollowsOne;
start_date & dash & date_2 & comma & CollapseDateList( RightValues( dates; countDates - 2 ); comma; dash );
// first two values are not sequential
// default
GetValue ( dates ; 1 ) & comma & CollapseDateList( RightValues( dates; countDates - 1 ); comma; dash )
)
)
)
)