2010-02-04 26 views
16

Ho due grandi array con circa 1000 righe e 1000 colonne. Ho bisogno di confrontare ogni elemento di questi array e memorizzare 1 in un altro array se gli elementi corrispondenti sono uguali.Come faccio a confrontare tutti gli elementi di due array?

Posso farlo con cicli for ma ciò richiede molto tempo. Come posso farlo più velocemente?

+2

Sempre, sempre possibile vectorizzare il codice MATLAB quando possibile. – Doresoom

+0

Dovrebbe essere spostato su http://math.stackexchange.com/? – aaronsnoswell

risposta

12

Se le due matrici A e B sono delle stesse dimensioni, allora si può fare questo:

index = A == B; 

e index sarà un logical array con quelli di tutto il mondo un elemento di A e B sono uguali e zero altrimenti.

Una parola di avvertimento ...

Se A e B contengono numeri interi, quanto sopra dovrebbe andare bene. Tuttavia, se contengono valori in virgola mobile, potresti ottenere risultati indesiderati. Il codice sopra avrà solo i valori di uno per gli elementi che sono esattamente uguale a. Anche la più piccola differenza farà sì che gli elementi siano considerati non uguali.

È possibile consultare this question's answers per ulteriori informazioni su come gestire i "pericoli delle operazioni in virgola mobile". Una soluzione potrebbe essere quella di verificare che allineamento elementi sono all'interno di una determinata tolleranza l'uno dall'altro, in questo modo:

tolerance = 0.0001; 
index = abs(A-B) <= tolerance; 

È possibile che questo vi darà una matrice logica index con quelli di tutto il mondo gli elementi di A e B si trovano a 0,0001 di a vicenda e zero altrimenti.

+0

Matlab ha la funzione eps, descritta come precisione relativa in virgola mobile.Puoi usarlo al posto della variabile di tolleranza nel codice di gnovice. indice = abs (A-B) <= eps; – yuk

+0

eps è il valore più piccolo che può essere rappresentato, non è vero? Non è molto utile in questo contesto. –

7

Basta usare il normale == dell'operatore:

>> [1 2; 3 4] == [1 5; 6 4]  

ans = 

    1  0 
    0  1 
29

Le risposte date sono tutti corretti. Volevo solo elaborare il commento gnovice's sul test in virgola mobile.

Quando si confrontano i numeri in virgola mobile per l'uguaglianza, è necessario utilizzare un valore di tolleranza. Vengono comunemente utilizzati due tipi di confronti di tolleranza: tolleranza assoluta e tolleranza relativa. (source)

Un paragone tolleranza assoluta di a e b assomiglia:

|a-b| < tol 

Un confronto relativa tolleranza assomiglia:

|a-b| < tol*max(|a|,|b|) + tol_floor 

È possibile implementare queste due funzioni anonime:

%# absolute tolerance equality 
isequalAbs = @(x,y,tol) (abs(x-y) <= tol); 

%# relative tolerance equality 
isequalRel = @(x,y,tol) (abs(x-y) <= (tol*max(abs(x),abs(y)) + eps)); 

Quindi è possibile utilizzarli come:

%# let x and y be scalars/vectors/matrices of same size 
x == y 
isequalAbs(x, y, 1e-6) 
isequalRel(x, y, 1e-6) 
+0

Cosa c'è di sbagliato in 'isequal'? – Jacob

+4

provare: 'isequal (0.3,0.1 * 3)' che è equivalente a '0.3 == 0.1 * 3'. La risposta in entrambi è falsa! – Amro

+1

Le mie scuse - Suppongo che la mia fiducia in MATLAB sia stata malriposta! Ora devo cambiare un sacco di codice :( – Jacob

Problemi correlati