2014-07-07 12 views
6

Avviso in anticipo: al momento posso essere completamente confuso. Racconto una breve storia su ciò che effettivamente cerco di ottenere perché potrebbe chiarire le cose. Diciamo che ho f(a,b,c,d,e) e voglio trovare arg max (d,e) f(a,b,c,d,e). Si consideri un (esempio banale di una) di griglia discretizzata F di f:Valutazione dell'array al subarray specifico

F = np.tile(np.arange(0,10,0.1)[newaxis,newaxis,:,newaxis,newaxis], [10, 10, 1, 10, 10]) 
maxE = F.max(axis=-1) 
argmaxD = maxE.argmax(axis=-1) 
maxD = F.max(axis=-2) 
argmaxE = maxD.argmax(axis=-1) 

Questo è il caso come io di solito risolvere la versione discretizzata. Ma ora assumiamo invece che io voglia risolvere arg max d f(a,b,c,d,e=X): Invece di scegliere in modo ottimale e per ogni altro input, e è un numero fisso e dato (di dimensione AxBxCxD, che in questo esempio sarebbe 10x10x100x10). Ho problemi a risolvere questo.

Il mio approccio ingenuo era

X = np.tile(np.arange(0,10)[newaxis,newaxis,:,newaxis], [10,10,1,10]) 
maxX = F[X] 
argmaxD = maxX.argmax(axis=-1) 

Tuttavia, l'enorme ondata di memoria che blocca il mio IDE implica che F[X] non è evidentemente quello che stavo cercando.

Le prestazioni sono fondamentali.

+0

sembra ciò che si vuole è qualcosa di simile: 'np.argmax (np.max (F, asse = -1), asse = -1)' –

risposta

2

credo che si può fare in questo modo, ma forse c'è un modo migliore ..

n = 10 
F = np.tile(np.arange(0,n,0.1)[None,None,:,None,None], [n, n, 1, n, n]) 
X = np.tile(np.arange(0,n)[None,None,:,None], [n, n, 1, n]) 

a,b,c,d = np.ogrid[:n,:n,:n,:n] 
argmaxD = F[a,b,c,d,X].argmax(axis=-1) 

Sopra X non occupa tutto lo spazio, come abbiamo discusso nei commenti. Se si desidera scegliere e per tutti a, b, c e d si potrebbe fare ad es .:

X = np.tile(np.arange(0,n,0.1).astype(int)[None,None,:,None], [n, n, 1, n]) 
a,b,c,d = np.ogrid[:n,:n,:100,:n] 
argmaxD = F[a,b,c,d,X].argmax(axis=-1) 

Inoltre, si noti che invece di tile si potrebbe fare uso di trasmissioni. Ma poi F[a,b,c,d,X] ha una dimensione singolare così si dovrebbe fornire qualcosa come axis=3:

X = np.arange(0,n,0.1).astype(int)[None,None,:,None] 
a,b,c,d = np.ogrid[:n,:n,:100,:n] 
argmaxD = F[a,b,c,d,X].argmax(axis=3) 
+0

Senza pienamente digerire quello che sta succedendo qui: il mio vecchio 'argmaxD '(dalla massimizzazione standard) ha avuto' (10L, 10L, 100L) ', mentre' argmaxD' ha forma '(10L, 10L, 10L)'. Dato che dovrebbe essere il maximizer ottimale dato '(a, b, c)', che ha la forma '(10, 10, 100)', questo non può essere corretto. – FooBar

+0

@FooBar, avevo già notato le diverse dimensioni in una delle dimensioni, ma questo è il risultato della scelta di 'X = np.tile (np.arange (0, n), ...'. Suppongo che dovresti solo inserire la dimensione '0.1', quindi dovresti usare anche' np.ogrid [: n,: n,: 100,: n] ' –

+0

' 0.1' stepsize fornisce 'IndexError', dato che deve essere intero.' X' necessita per contenere valori interi per ciò che abbiamo selezionato fuori dalla griglia per 'e'.' e' contiene elementi '100'. Ciò significa che dobbiamo selezionare tra' (0, 99) 'per' e', giusto? Ho provato 'X = np.tile (np.arange (0,100) ...)', ma ottengo un 'IndexError' ... So che sto facendo un errore, non riesco a riconoscerlo. – FooBar

0

Questa sarebbe la mia idea per risolvere questo.

from itertools import product, starmap 

f = lambda a,b,c,d,e : d/e 

args_iterable = product([1],[2],[3],range(1,1000),range(1,1000)) 

max_val, max_args = max(starmap(lambda *args: (f(*args), args) , args_iterable)) 

print max_args