3 Stimmen

Messen Sie, wie weit die Daten in einem Array verteilt sind

Ich habe ein Array von Nullen und Einsen und ich muss wissen, ob die Daten über die Spalten verteilt oder in Klumpen konzentriert sind.

Zum Beispiel:

Wenn ich das Array x habe und es diese Werte hat:

Spalte 1 Werte: 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1

Spalte 2 Werte: 1 0 0 1 0 0 0 0 0 0 0 1 0 0 0 0 1 0 0 1 0 0 0 1

Wenn wir die Anzahl der Einsen zählen, können wir feststellen, dass sie gleich ist, aber die Einsen in Spalte 2 sind besser verteilt und verteilt im Vergleich zu Spalte 1.

Ich versuche eine Punktzahl zu erstellen, die mir einen hohen Wert gibt, wenn die Verteilung gut ist, und einen niedrigen Wert, wenn die Verteilung schlecht ist ... irgendwelche Ideen??

Datenbeispiel:

1 0 0 0 5 0 -2 -3  0 0 1
1 0 0 0 0 0  0  0  0 0 1
2 0 0 0 0 0  0  3 -3 1 0
1 2 3 0 5 0  2 13  4 5 1
1 0 0 0 0 0 -4 34  0 0 1

2voto

Divakar Punkte 211985

Ich denke, du würdest einen Intervall benötigen, um die "Streuung" lokal zu finden, sonst würde die sample 1 (die in der Frage als Column 1 bezeichnet wird) zwischen dem 2. und 3. erscheinen.

Also, basierend auf dieser Theorie und unter der Annahme, dass input_array das Eingabearray ist, kannst du diesen Ansatz ausprobieren -

intv = 10; %// Intervall
diff_loc = diff(find(input_array))
spread_factor = sum(diff_loc(diff_loc<=intv)) %// gewünschte Ausgabe/Punktzahl

Für sample 1 ergibt sich spread_factor als 4 und für sample 2 ist es 23.


Eine andere Theorie, die du anwenden könntest, wäre, wenn du von einem Intervall ausgehst, so dass der Abstand zwischen aufeinanderfolgenden Zahlen größer oder gleich diesem Intervall sein muss. Diese Theorie würde uns zu einem Code wie diesem führen -

intv = 3; %// Intervall
diff_loc = diff(find(input_array))
spread_factor = sum(diff_loc>=intv)

Mit diesem neuen Ansatz - Für sample 1 ist spread_factor 1 und für sample 2 ist es 5.

2voto

Dan Punkte 44204

Ich denke, was Sie zu messen versuchen, ist die Varianz der Verteilung der Anzahl von 0s zwischen den 1n, d.h.:

f = @(x)std(diff(find(x)))

Also für Ihre Daten:

a = [1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1]
b = [1 0 0 1 0 0 0 0 0 0 0 1 0 0 0 0 1 0 0 1 0 0 0 1]

f(a)
    = 8.0498

f(b)
    = 2.0736

Aber ich denke immer noch, dass Sie im Wesentlichen versuchen, die Störung des Systems zu messen, was ich mir vorstelle, dass Entropie misst, aber ich weiß nicht wie.

Beachten Sie, dass dies einen niedrigen Wert liefert, wenn die "Verbreitung" gut ist, und einen hohen Wert, wenn sie schlecht ist (d.h. das Gegenteil Ihrer Anfrage).

Wenn Sie es auch pro Spalte möchten, wird es etwas komplizierter:

f = @(x)arrayfun(@(y)std(diff(find(x(:,y)))), 1:size(x,2))
data = [a', b'];
f(data)

WARNUNG: Diese Methode berücksichtigt praktisch nicht die nachfolgenden und führenden 0s. Ich weiß nicht, ob das ein Problem ist oder nicht. aber im Grunde gibt f([0; 0; 0; 1; 1; 1; 0; 0; 0]) zurück 0 wohingegen f([1; 0; 0; 1; 0; 1; 0; 0; 0]) ein positives Ergebnis liefert, was (fälschlicherweise) darauf hindeutet, dass der erste Fall gleichmäßiger verteilt ist. Eine mögliche Lösung wäre, eine Zeile mit Einsen der Matrix voranzustellen und anzuhängen...

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X