2017-03-09 1 views
0

Need einige Ideen zu diesem Thema. Ich bin mir sicher, dass es einen cleveren Python-Weg gibt, dies zu tun, ohne auf eine "zellenweise" Neuerstellung des Arrays zurückzugreifen.Ordnen Sie Spalten in numpy Array basierend auf Inhalt (Zählung eines bestimmten Werts)

Hintergrund: Ich versuche eine große Zusammenfassung aus einem System zu manipulieren, das wir verwenden, um Crowd Worker Urteile zu sammeln. Ich formatiere die Daten so, dass es in einem geeigneten Format ist, um OpenBugs und möglicherweise später PyMC zu schieben.

Ich habe eine große NP-Array im folgenden Format, es gibt bis zu 500 Spalten und viele 1000 Zeilen. Dies ist ein reduziertes Beispiel:

a = np.array([['a','b','c','d','e'], 
      [1, 2, 3, 4, 5], 
      [1, 2, 'na', 'na','na'], 
      [1, 2, 'na', 4, 5]]) 

Gewünschtes Ergebnis: ich neu anordnen möge (im Idealfall Inplace) die Spalten der Daten, so dass sie durch die Anzahl des 'na' sortiert werden, die in der Spalte angezeigt. NB i nicht möchten nach einem col sortieren. Sortieren Sie die Spalten lieber selbst.

Ich möchte eine Option, um anzugeben, wie viele führende Spalten allein gelassen werden (nicht verschoben), da dies von Zeit zu Zeit abhängt. Und sortieren nach aufsteigend/absteigend. Die obere Zeile ist eine Kopfzeile, deren Werte die Spalte indizieren. Alle Werte sind entweder int oder 'na' und der Header ist eine Zeichenkette.

so in diesem Beispiel. Wenn ich 'a' col an ihrem Platz bleiben will, und sortiert nach absteigend Anzahl von 'na würde der Ausgang sein:

a = np.array([['a','c','d','e','b'], 
       [1, 3, 4, 5, 2], 
       [1, 'na', 'na', 'na',2], 
       [1, 'na', 4, 5, 2]]) 

jede kluge Array Manipulation Vorschläge willkommen!

+0

Hat die veröffentlichte Lösung für Sie funktioniert? – Divakar

Antwort

0

Ein Ansatz wäre -

N = 1 # No. of leading cols to be kept 
out = a[:,np.r_[:N,(-(a[:,N:]=='na').sum(0)).argsort()+N]] 

Grundsätzlich haben wir alle Spalten nach N auswählen, vergleichen gegen 'na' und bekommen die Anzahl pro Spalte mit .sum(0) und argsort Indizes immer in absteigender Reihenfolge. Schließlich verketten wir uns mit einer Reihe von Indizes bis N mit diesen argsort Indizes und Indexierung in die Spalten der Eingabe-Array, um uns die gewünschte Ausgabe zu geben.

Beispielläufe -

In [89]: a 
Out[89]: 
array([['a', 'b', 'c', 'd', 'e'], 
     ['1', '2', '3', '4', '5'], 
     ['1', '2', 'na', 'na', 'na'], 
     ['1', '2', 'na', '4', '5']], 
     dtype='|S2') 

In [90]: N = 1 # No. of leading cols to be kept 

In [91]: a[:,np.r_[:N,(-(a[:,N:]=='na').sum(0)).argsort()+N]] 
Out[91]: 
array([['a', 'c', 'd', 'e', 'b'], 
     ['1', '3', '4', '5', '2'], 
     ['1', 'na', 'na', 'na', '2'], 
     ['1', 'na', '4', '5', '2']], 
     dtype='|S2') 

In [92]: N = 2 # No. of leading cols to be kept 

In [93]: a[:,np.r_[:N,(-(a[:,N:]=='na').sum(0)).argsort()+N]] 
Out[93]: 
array([['a', 'b', 'c', 'd', 'e'], 
     ['1', '2', '3', '4', '5'], 
     ['1', '2', 'na', 'na', 'na'], 
     ['1', '2', 'na', '4', '5']], 
     dtype='|S2') 

Wenn die Reihenfolge der Spalten, die gleich Grafen von 'na' haben spielt keine Rolle, eine leistungsfähigere Lösung würde die negation des Eingangsfeldes wird vermieden für immer, dass durch stattdessen absteigende Reihenfolge umzukehren die argsort Indizes ohne Negation, so -

a[:,np.r_[:N,(a[:,N:]=='na').sum(0).argsort()[::-1]+N]] 
Verwandte Themen