J'ai utilisé différentes méthodes pour calculer à la fois le rang d'une matrice et la solution d'un système matriciel d'équations. Je suis tombé sur la fonction linalg.svd. En comparant cela à mes propres efforts pour résoudre le système avec l'élimination gaussienne, cela semble être à la fois plus rapide et plus précis. J'essaie de comprendre comment cela est possible.
Pour autant que je sache, la fonction linalg.svd utilise un algorithme QR pour calculer les valeurs propres de ma matrice. Je sais comment cela fonctionne mathématiquement, mais je ne sais pas comment Numpy parvient à le faire si rapidement et sans perdre beaucoup de précision.
Donc ma question: comment fonctionne la fonction numpy.svd, et plus précisément, comment parvient-elle à le faire rapidement et avec précision (par rapport à l'élimination gaussienne)?
la source
dgesdd
pour les SVD à valeur réelle. Donc, votre vraie question est probablement "comment fonctionne Lapack dgesdd?", Et c'est assez hors sujet pour stackoverflow.Réponses:
Il y a un certain nombre de problèmes dans votre question.
N'utilisez pas d'élimination gaussienne (factorisation LU) pour calculer le rang numérique d'une matrice. La factorisation LU n'est pas fiable à cet effet en arithmétique à virgule flottante. Utilisez plutôt une décomposition QR révélatrice de rang (comme
xGEQPX
ouxGEPQY
dans LAPACK, où x est C, D, S ou Z, bien que ces routines soient difficiles à retrouver; voir la réponse de JedBrown sur une question connexe ), ou utilisez un SVD (décomposition de valeurs singulières, commexGESDD
ouxGESVD
, où x est à nouveau C, D, S ou Z). Le SVD est un algorithme plus précis et fiable pour la détermination du rang numérique, mais il nécessite plus d'opérations en virgule flottante.Cependant, pour résoudre un système linéaire, la factorisation LU (avec pivotement partiel, qui est l'implémentation standard dans LAPACK) est extrêmement fiable dans la pratique. Il existe certains cas pathologiques pour lesquels la factorisation LU avec pivotement partiel est instable (voir la leçon 22 en Algèbre linéaire numériquepar Trefethen et Bau pour plus de détails). La factorisation QR est un algorithme numérique plus stable pour résoudre des systèmes linéaires, c'est probablement pourquoi il vous donne des résultats aussi précis. Cependant, cela nécessite plus d'opérations en virgule flottante que la factorisation LU par un facteur 2 pour les matrices carrées (je crois; JackPoulson peut me corriger à ce sujet). Pour les systèmes rectangulaires, la factorisation QR est un meilleur choix car elle donnera des solutions des moindres carrés à des systèmes linéaires surdéterminés. SVD peut également être utilisé pour résoudre des systèmes linéaires, mais il sera plus coûteux que la factorisation QR.
janneb a raison que numpy.linalg.svd est un wrapper
xGESDD
dans LAPACK. Les décompositions de valeurs singulières se déroulent en deux étapes. Premièrement, la matrice à décomposer est réduite à une forme bidiagonale. L'algorithme utilisé pour réduire à la forme bidiagonale dans LAPACK est probablement l'algorithme de Lawson-Hanson-Chan, et il utilise la factorisation QR à un moment donné. La leçon 31 en Algèbre linéaire numérique de Trefethen et Bau donne un aperçu de ce processus. Ensuite,xGESDD
utilise un algorithme de division et de conquête pour calculer les valeurs singulières et les vecteurs singuliers gauche et droit à partir de la matrice bidiagonale. Pour obtenir des informations sur cette étape, vous devrez consulter Matrix Computations de Golub et Van Loan, ou Applied Numerical Linear Algebra de Jim Demmel.Enfin, vous ne devez pas confondre les valeurs singulières avec les valeurs propres . Ces deux ensembles de quantités ne sont pas identiques. Le SVD calcule les valeurs singulières d'une matrice. Le calcul numérique de Cleve Moler avec MATLAB donne un bon aperçu des différences entre les valeurs singulières et les valeurs propres . En général, il n'y a pas de relation évidente entre les valeurs singulières d'une matrice donnée et ses valeurs propres, sauf dans le cas des matrices normales , où les valeurs singulières sont la valeur absolue des valeurs propres.
la source
rank
fonction). Il y a aussi un peu de discrétion lors de l'utilisation de l'une ou l'autre approche; dans l'approche SVD, le rang numérique est le nombre de valeurs singulières au-dessus d'un seuil spécifié (généralement très petit). (L'approche QR est similaire, mais remplace les valeurs singulières par des entrées diagonales de la matrice R.)En raison du libellé de votre question, je suppose que votre matrice est carrée. Les routines SVD de LAPACK, telles que zgesvd , procèdent essentiellement en trois étapes pour les matrices carrées:
la source
numpy.linalg.svd is a wrapper around {Z,D}GESDD from LAPACK. LAPACK, in turn, is very carefully written by some of the world's foremost experts in numerical linear algebra. Indeed, it'd be very surprising if someone not intimately familiar with the field would succeed in beating LAPACK (either in speed or accuracy).
As for why QR is better than Gaussian elimination, that is probably more appropriate for /scicomp//
la source