Ich versuche einen schnellen Weg zu finden, um eindeutige Werte in einem Array zu finden und 0
als Möglichkeit für einen eindeutigen Wert zu entfernen.
Im Moment habe ich zwei Lösungen:
%Vor% dataArray
entspricht:
In diesem Fall ist result1
gleich [1; 2]
und result2
ist gleich [0; 1; 2]
.
Die Funktion unique
ist schneller, aber ich möchte nicht, dass 0
berücksichtigt wird. Gibt es eine Möglichkeit, dies mit unique
zu tun und nicht 0
als eindeutigen Wert zu betrachten? Gibt es eine andere Alternative?
BEARBEITEN
Ich wollte die verschiedenen Lösungen zeitlich anpassen.
%Vor%Und die Ergebnisse:
%Vor% Die Lösung mit sparse
und accumarray
funktioniert jedoch nur mit integer
. Diese Lösungen funktionieren nicht mit double
.
Hier ist ein verrückter Vorschlag mit accumarray
, demonstriert mit Floris 'Testdaten:
Danke an Luis Mendo, der darauf hingewiesen hat, dass mit nonzeros
result = result(result>0)
! nicht ausgeführt werden muss!
Beachten Sie, dass diese Lösung Daten mit ganzzahligen Werten benötigt (nicht unbedingt ein ganzzahliger Datentyp, sondern nur nicht mit dezimalen Komponenten). Das Vergleichen von Gleitkommawerten für die Gleichheit, wie es unique
tun würde, ist gefährlich. Siehe hier und hier .
Ursprünglicher Vorschlag: Kombiniere unique
mit setdiff
:
Oder entfernen Sie mit der logischen Indizierung nach unique
:
Im Allgemeinen bevorzuge ich die Zuweisung von []
in ( result(result==0)=[];
), da es für große Datensätze sehr ineffizient wird.
Das Entfernen von Nullen nach unique
sollte schneller sein, da es mit weniger Daten arbeitet (es sei denn, jedes Element ist eindeutig, ODER wenn a
/ dataArray
sehr kurz ist).
Um dem allgemeinen Lärm noch etwas hinzuzufügen - hier sind drei verschiedene Methoden. Sie alle geben die gleiche Antwort, aber etwas andere Zeiten:
%Vor%Auf meinem Computer waren die Timings (für ein Array von 100000 Elementen) wie folgt:
%Vor% Ich mag immer sparse
für ein Problem wie dieses - Sie erhalten die Anzahl der Elemente gleichzeitig mit ihren eindeutigen Werten.
BEARBEITEN nach dem Vorschlag von @ chappj. Ich habe eine vierte Option hinzugefügt
%Vor%Zeit:
%Vor%Meine Damen und Herren, wir haben einen Gewinner.
AFTERWORD Die indexbasierten Methoden ( sparse
und accumarray
) arbeiten nur mit Eingaben mit ganzzahligen Werten (obwohl sie vom Typ double
sein können). Dies schien auf der Grundlage des in der Frage angegebenen Eingabearrays OK zu sein, funktioniert jedoch nicht bei nicht ganzzahligen Eingängen. Natürlich ist unique
ein kniffliges Konzept, wenn man verdoppelt - die Zahl, die "gleich" aussieht, kann unterschiedlich dargestellt werden. Sie könnten das Eingabearray abschneiden (die Daten bereinigen), um sicherzustellen, dass dies kein Problem ist. Zum Beispiel, wenn Sie
Sie würden alle Werte auf nicht mehr als 3 signifikante Zahlen runden, und weil Sie "über ein int" gegangen sind, sind Sie sicher, dass Sie nicht mit Werten enden, die "sehr subtil verschieden" sind (sagen wir in der achten Ziffer) oder darüber hinaus). Natürlich könntest du in diesem Fall auch
machen %Vor% Dies ist "ziemlich robust" für nicht ganzzahlige Werte (im obigen Fall behandelt es Werte mit bis zu drei signifikanten Stellen; wenn Sie mehr benötigen, wird der Platzbedarf irgendwann zu groß und diese Methode wird langsamer als unique
, welches die Daten tatsächlich sortieren muss.)