| 

.NET C# Java Javascript Exception

0
Hallo Allerseits,
ich habe mir eine Extension geschrieben die prüfen soll ob die Werte (zb. Int, Double, oder auch eine Mischung.) in einer übergebenen List fortlaufend sind. Das Problem besteht darin das oldVal den kleinst Möglichen Wert enthalten soll damit die Schleife beim ersten durchlauf erfolgreich Comparen kann. Allerdings ist es hier immer NULL da. Hat jemand eine Idee wie sich das lösen lässt?

Beispiel für den Aufruf der Extension
Dim myList = New List(Of IComparable)(New Integer() {1, 2, 3, 4, 5})
Console.WriteLine(myList.IsSuccsessive()) 'Sollte True sein

Dim myList2 = New List(Of IComparable)(New Double() {1, 2, 30, 4, 5})
Console.WriteLine(myList2.IsSuccsessive()) 'Sollte False sein

'Gemischte Liste
Dim myList3 = New List(Of IComparable)
myList3.Add(1) 'int
myList3.Add(2) 'int
myList3.Add(2.5) 'Double
myList3.Add(3) 'int
Console.WriteLine(myList.IsSuccsessive()) 'Sollte True sein



Extension Method:

public static bool IsSuccsessive<T>(this IEnumerable<T> input) where T : IComparable
{
if ((input==null) || (input.Count()==0)) return true;

var oldVal = default(T);

foreach (var val in input)
{
if (oldVal.CompareTo(val) == 1) return false;

oldVal = val;
}

return true;
}
23.03.2011
Thomas Sczyrba 1,3k 1 1 9
3 Antworten
3
Probier doch mal das:

public static bool IsSuccsessive<T>(this IEnumerable<T> input) where T : IComparable
{
if ((input == null) || (input.Count() == 0)) return true;

var oldVal = input.First();

foreach (var val in input.Skip(1))
{
if (oldVal.CompareTo(val) > 0) return false;

oldVal = val;
}

return true;
}
23.03.2011
Matthias Hlawatsch 8,4k 2 8
An das kleine Skip habe ich nicht gedacht. Das war des Rätsels Lösung. Klasse thx
Thomas Sczyrba 23.03.2011
es hat auch ohne skip funktioniert ABER: -> kommentar in meiner antwort
nabuchodonossor 23.03.2011
2
Stimmt, es funktioniert auch ohne Skip - solange aufeinderfolgende gleiche Werte ok sind. Dann ist Skip einfach nur eine Optimierung (sowohl der Laufzeit als auch der Verständlichkeit). Wenn auf "strenges" Aufsteigen geprüft werden soll, ist Skip aber nötig.
Übrigens: CompareTo garantiert nicht, dass es 1 liefert. Deshalb sollte das Ergebnis nur mit 0 verglichen werden, nicht mit 1. Habe mein Beispiel entsprechend angepasst.
Matthias Hlawatsch 23.03.2011
Nochmal in der Doku nachgesehen, du hast recht, es könnte auch jeder andere Wert grösser 0 daherkommen. Was aber dann wiederum bedeutet, dass die Abfrage nicht > 0, sondern < 1 sein sollte - FALLS aufeinanderfolgende gleichbleibende Werte erlaubt sind.
nabuchodonossor 23.03.2011
ja, und noch mal herumprobiert, die Methode mit skip ist natürlich elegant! das mit < und > ist natürlich auch so eine sache: ich hab in meinen tests nämlich nicht den alten mit dem neuen, sondern den neue mit dem alten verglichen ... da komme ich schon mal durcheinander.
nabuchodonossor 23.03.2011
Guter Hinweis mit dem CompareTo vergleichsoperator. Meine Ursprünglicher Version mit ==1 ist auf die Nase gefallen. Damit geprüft wird ob aufsteigende Werte enthalten sind (zweimal die gleiche Zahl hintereinander ist nicht aufsteigend) benutze ich jetzt : oldVal.CompareTo(val) > -1 :-)
Thomas Sczyrba 23.03.2011
Freut mich, dass ich helfen konnte :-)
Auch wenn es funktional äquivalent ist: schreib lieber oldVal.CompareTo(val) >= 0. Liest sich leichter - jedenfalls gehe ich mal davon aus, dass ich nicht der einzige bin, der sich die Verwendung von CompareTo so merkt:
linkerOperand Operator rechterOperand
entspricht
linkerOperand.CompareTo(rechterOperand) Operator 0.
Der Punkt ist, dass ich dann beim Denken/Schreiben/Lesen den gleichen Operator verwende, während in Deiner Variante das geschriebene ">" ein logisches ">=" bedeutet.
Matthias Hlawatsch 23.03.2011
+1 Tolle Antwort!
Joachim 25.03.2011
2
Müsstest du nicht oldVal auf den ERSTEN Eintrag deiner Liste setzen?
23.03.2011
nabuchodonossor 1,2k 4
Was meinst du genau mit "kleinst" möglichen Wert?
nabuchodonossor 23.03.2011
Und ausserdem funktioniert es bei mir, mehr oder weniger. Die Werte 10, 11, 13 ergeben true, obwohl sie nicht forlaufend sind, weil comparto ja nur sagt ist grösser oder kleiner oder gleich, aber nicht sagt, wieviel grösser oder kleiner.
nabuchodonossor 23.03.2011
1
Und das Hauptproblem sehe ich in der Vermischun von int und double: Wenn 11, 12, 13 true ist, wirst du wahrscheinlich auch haben wollen, dass 11.0, 12.0, 13.0 true ergibt. Aber meiner Ansicht nach könnte auch 11.001, 11.002, 11.003 eine fortlaufende Kette bilden.
Dalso da würde ich nochmal drüber nachdenken.
nabuchodonossor 23.03.2011
Ja das mit den ERSTEN Eintrag ist korrekt. Das in Verbindung mit Skip hats gebracht. Mit "fortlaufend" war gemeint das der Nachfolgende Wert nicht kleiner sein darf wie der vorhergehende. Die Abstände zwischen den Werten sind hierbei egal
Thomas Sczyrba 23.03.2011
Wenn der nachfolgende Wert GLEICH sein darf, musst du das von == 1 noch auf < 1 ändern.
nabuchodonossor 23.03.2011
2
"nicht GLEICH sein darf", wolltest Du schreiben, oder? "< 1" führt dazu, dass ein Ergebnis von 0, also Gleichheit, die Schleife mit false abbricht, d.h. aufeinderfolgende gleiche Werte ergeben false als Ergebnis.
Und, wie ich bei meiner Antwort angemerkt habe: es ist besser, mit 0 zu vergleichen. Laut Doku kann CompareTo irgendwas zurückgeben, nur das Vorzeichen ist garantiert.
Matthias Hlawatsch 23.03.2011
sieht so aus, als ob du meine gedanken besser liest als ich *g*
nabuchodonossor 23.03.2011
2
seh ich auch wie nabuchodonossor so da es ja auch sein könnte das der erster wert der List negativ ist.

'ich würde anstelle von:'
var oldVal = default(T);

'etwas wie:'
var oldval=input[0];
'benutzen.

Dann sollte es auch Problemlos funktionieren.
23.03.2011
1
Egal wie man die Logik formuliert, es kommt bei dem Code Beispiel solange true raus, solange die nächste Zahl größer ist, also die Methode IsSuccessive sagt nur "aufsteigend" oder eben nicht, nicht aber zusammenhängend aufsteigend.
nabuchodonossor 23.03.2011
1
Da Thomas speziell nach der Initialisierung beim ersten Schleifendurchlauf gefragt hat, gehe ich mal davon aus, dass er mit dem Code innerhalb der Schleife zufrieden ist. Das Beispiel mit double würde sonst ja auch keinen Sinn ergeben - 2.5 hat keinen Nachfolger. Dann leistet die Methode aber tatsächlich 'nur' "IstAufsteigend".
Matthias Hlawatsch 23.03.2011

Stelle deine .net-Frage jetzt!