Moltiplicazione della matrice MATLAB (il miglior approccio computazionale)


10

Devo effettuare una trasformazione delle coordinate tra due sistemi di riferimento (assi). Per questo, tre matrici ( ) devono essere moltiplicate a causa dell'utilizzo di alcuni assi intermedi. Ho pensato a due approcci per risolvere questo:3×3

Metodo n. 1 : esecuzione diretta della moltiplicazione, ovvero

vf=R1 R2 R3 vi

Metodo n. 2 : suddiviso in passaggi:

  1. v3i=R3 vi
  2. v23=R2 v3i
  3. vf=R1 v23

dove:

, R 2 e R 3 sonomatrici 3 × 3R1R2R33×3

, v i , v 3 i , v 23 sonovettori 3 × 1vfviv3iv233×1

Vorrei sapere quale metodo è più efficiente dal punto di vista computazionale (meno tempo) per effettuare la trasformazione (questo verrà fatto molte volte).



@ChrisTaylor: Grazie mille per il tuo suggerimento.
julianfperez,

2
Per favore, non fare il crosspost.
Strappato

2
Nota, c'erano due domande incrociate qui e StackOverflow. Le domande, i loro commenti e risposte sono stati fusi in questo.
Aron Ahmadia,

@Will and AronAhmadia: mi dispiace. Non sapevo che il crossposting fosse proibito. Ho sempre pubblicato le mie domande su StackOverflow ma oggi ho trovato questo nuovo sito e ho pensato che forse avrei potuto trovare aiuto anche qui.
julianfperez,

Risposte:


17

ABCvA(B(Cv))

A(B(Cv))

Per scoprire in generale come misurare l'impatto delle piccole differenze di programmazione sui calcoli su larga scala, scrivere al prompt di Matlab "profilo di aiuto".


Grazie per le informazioni interessanti fornite nella tua risposta.
julianfperez,

Perché è più veloce se si salvano gli intermedi?
Federico Poloni,

@FedericoPoloni: avevo scritto che è leggermente più veloce non salvare gli intermedi.
Arnold Neumaier,

@ArnoldNeumaier Ooh scusa se ho letto male. :)
Federico Poloni,

14

Per cominciare, non userei variabili intermedie, ma parentesi. A meno che, ovviamente, non ti interessino i risultati intermedi, ma suppongo di no.

Ho provato quanto segue in Matlab:

>> N = 500;                                             
>> A = rand(N); B = rand(N); C = rand(N); v = rand(N,1);

>> tic, for k=1:100, A*B*C*v; end; toc
Elapsed time is 3.207299 seconds.

>> tic, for k=1:100, A*(B*(C*v)); end; toc
Elapsed time is 0.108095 seconds.

Devo dire, tuttavia, che questo è abbastanza spaventoso. Ho sempre pensato che Matlab sarebbe stato intelligente riguardo all'ordine di moltiplicazione di matrici, poiché si tratta di un problema noto con soluzioni semplici ed efficienti.


Ti sei perso la parte in cui le matrici sono 3x3? :)
Aron Ahmadia,

2
@AronAhmadia: Oops ... Mi mancava, grazie. Immagino per quelle dimensioni delle matrici, l'intero problema è controverso, ma sono ancora sorpreso dai risultati per il grande N.
Pedro

7
Immagino che MATLAB stia seguendo le regole di precedenza C per la valutazione dell'espressione perché la matematica in virgola mobile non è associativa e devono presumere che tu sappia cosa stai facendo :)
Aron Ahmadia

2
@Pedro: grazie per la risposta. Per la dimensione matrice 3x3 ho verificato che anche la tua soluzione è migliore della solita moltiplicazione di matrice (senza parentesi).
julianfperez,

+1 grazie per aver mostrato un modo semplice e facile per misurare il tempo di esecuzione
Steven Magana-Zook,

14

Poiché le matrici sono così piccole, tutto il costo sarà in overhead di chiamata. Se eseguirai la trasformazione più volte, sarà più rapido eseguire il pre-calcolo D=A*B*Cuna volta e poi per ogni vettore applicato v_f=D*v_i. Puoi anche prendere in considerazione l'idea di portarlo in un file mex.


La ringrazio per la risposta. Nel mio caso, le matrici sono rotanti (dipendono da un valore angolare e questo cambia) quindi il prodotto A B C non è sempre lo stesso.
julianfperez,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.