Ich habe einige meiner Codes mit MATLAB-Codes "auf Lager" verglichen. Ich bin überrascht über das Ergebnis.
Ich habe einen Beispielcode ausgeführt (Sparse Matrix)
n = 5000;
a = diag(rand(n,1));
b = rand(n,1);
disp('For a\b');
tic;a\b;toc;
disp('For LU');
tic;LULU;toc;
disp('For Conj Grad');
tic;conjgrad(a,b,1e-8);toc;
disp('Inv(A)*B');
tic;inv(a)*b;toc;
Ergebnisse :
For a\b
Elapsed time is 0.052838 seconds.
For LU
Elapsed time is 7.441331 seconds.
For Conj Grad
Elapsed time is 3.819182 seconds.
Inv(A)*B
Elapsed time is 38.511110 seconds.
Für dichte Matrix:
n = 2000;
a = rand(n,n);
b = rand(n,1);
disp('For a\b');
tic;a\b;toc;
disp('For LU');
tic;LULU;toc;
disp('For Conj Grad');
tic;conjgrad(a,b,1e-8);toc;
disp('For INV(A)*B');
tic;inv(a)*b;toc;
Ergebnisse:
For a\b
Elapsed time is 0.575926 seconds.
For LU
Elapsed time is 0.654287 seconds.
For Conj Grad
Elapsed time is 9.875896 seconds.
Inv(A)*B
Elapsed time is 1.648074 seconds.
Wie zum Teufel ist a \ b so toll?
linear-algebra
performance
matlab
Anfrage
quelle
quelle
Antworten:
In Matlab ruft der Befehl '\' einen Algorithmus auf, der von der Struktur der Matrix A abhängt und Überprüfungen (geringer Overhead) der Eigenschaften von A enthält.
Um den Overhead zu reduzieren, können Sie den Befehl linsolve in Matlab verwenden und selbst einen geeigneten Löser aus diesen Optionen auswählen.
quelle
Wenn Sie sehen möchten, was
a\b
für Ihre spezielle Matrix funktioniert, können Sie genau festlegenspparms('spumoni',1)
und herausfinden, von welchem Algorithmus Sie beeindruckt waren. Beispielsweise:wird ausgegeben
Ich kann also sehen, dass "\" in diesem Fall "CHOLMOD" verwendet.
quelle
help mldivide
.Für dünne Matrizen verwendet Matlab UMFPACK für die "
\
Operation ", die in Ihrem Beispiel im Wesentlichen die Werte von durchläufta
, sie invertiert und mit den Werten von multipliziertb
. Für dieses Beispiel sollten Sie jedoch verwendenb./diag(a)
, was viel schneller ist.Bei dichten Systemen ist der Backslash-Operator etwas komplizierter. Eine kurze Beschreibung dessen, was wann getan wird, finden Sie hier . Gemäß dieser Beschreibung würde Matlab in Ihrem Beispiel
a\b
durch Rückwärtssubstitution lösen . Für allgemeine Quadratmatrizen wird eine LU-Zerlegung verwendet.quelle
tic; for k=1:100, a\b; end; toc
.Als Faustregel gilt, wenn Sie eine spärliche Matrix mit angemessener Komplexität haben (dh, es muss sich nicht um die 5-Punkt-Schablone handeln, sondern es kann sich tatsächlich um eine Diskretisierung der Stokes-Gleichungen handeln, für die die Anzahl der Nichtzeros pro Zeile gilt viel größer als 5), dann schlägt ein spärlicher direkter Löser wie UMFPACK normalerweise einen iterativen Krylov-Löser, wenn das Problem nicht größer als etwa 100.000 Unbekannte ist.
Mit anderen Worten, für die meisten spärlichen Matrizen, die aus 2D-Diskretisierungen resultieren, ist ein direkter Löser die schnellste Alternative. Nur bei 3D-Problemen, bei denen Sie schnell über 100.000 Unbekannte erreichen, muss ein iterativer Löser verwendet werden.
quelle