-
Couldn't load subscription status.
- Fork 196
linalg: Singular Value Decomposition #808
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
42aa3e5
e1d49d8
f5adf8f
64adda4
036c574
4a90c09
063b421
6abe7df
194f4a1
9de160b
cf40f75
32784cd
bb47ba5
3b365aa
ba5e5e7
6556e8b
9c2f133
88a49bb
cf15eb1
980a555
28ae2cb
69458ad
b579d98
8387797
e0d800c
6e5a7ce
8f35e98
173f1ee
bdffb4f
9f51efe
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
|
@@ -898,3 +898,95 @@ Exceptions trigger an `error stop`. | |||||||||||
| ```fortran | ||||||||||||
| {!example/linalg/example_determinant2.f90!} | ||||||||||||
| ``` | ||||||||||||
|
|
||||||||||||
| ## `svd` - Compute the singular value decomposition of a rank-2 array (matrix). | ||||||||||||
|
|
||||||||||||
| ### Status | ||||||||||||
|
|
||||||||||||
| Experimental | ||||||||||||
|
|
||||||||||||
| ### Description | ||||||||||||
|
|
||||||||||||
| This subroutine computes the singular value decomposition of a `real` or `complex` rank-2 array (matrix) \( A = U \cdot S \cdot \V^T \). | ||||||||||||
| The solver is based on LAPACK's `*GESDD` backends. | ||||||||||||
|
|
||||||||||||
| Result vector `s` returns the array of singular values on the diagonal of \( S \). | ||||||||||||
| If requested, `u` contains the left singular vectors, as columns of \( U \). | ||||||||||||
| If requested, `vt` contains the right singular vectors, as rows of \( V^T \). | ||||||||||||
|
|
||||||||||||
| ### Syntax | ||||||||||||
|
|
||||||||||||
| `call ` [[stdlib_linalg(module):svd(interface)]] `(a, s, [, u, vt, overwrite_a, full_matrices, err])` | ||||||||||||
|
|
||||||||||||
| ### Class | ||||||||||||
| Subroutine | ||||||||||||
|
|
||||||||||||
| ### Arguments | ||||||||||||
|
|
||||||||||||
| `a`: Shall be a rank-2 `real` or `complex` array containing the coefficient matrix of size `[m,n]`. It is an `intent(inout)` argument, but returns unchanged unless `overwrite_a=.true.`. | ||||||||||||
|
|
||||||||||||
| `s`: Shall be a rank-1 `real` array, returning the list of `k = min(m,n)` singular values. It is an `intent(out)` argument. | ||||||||||||
|
|
||||||||||||
| `u` (optional): Shall be a rank-2 array of same kind as `a`, returning the left singular vectors of `a` as columns. Its size should be `[m,m]` unless `full_matrices=.false.`, in which case, it can be `[m,min(m,n)]`. It is an `intent(out)` argument. | ||||||||||||
|
|
||||||||||||
| `vt` (optional): Shall be a rank-2 array of same kind as `a`, returning the right singular vectors of `a` as rows. Its size should be `[n,n]` unless `full_matrices=.false.`, in which case, it can be `[min(m,n),n]`. It is an `intent(out)` argument. | ||||||||||||
|
|
||||||||||||
| `overwrite_a` (optional): Shall be an input `logical` flag. If `.true.`, input matrix `A` will be used as temporary storage and overwritten. This avoids internal data allocation. By default, `overwrite_a=.false.`. It is an `intent(in)` argument. | ||||||||||||
|
|
||||||||||||
| `full_matrices` (optional): Shall be an input `logical` flag. If `.true.` (default), matrices `u` and `vt` shall be full-sized. Otherwise, their secondary dimension can be resized to `min(m,n)`. See `u`, `v` for details. | ||||||||||||
|
|
||||||||||||
| `err` (optional): Shall be a `type(linalg_state_type)` value. This is an `intent(out)` argument. | ||||||||||||
|
|
||||||||||||
| ### Return values | ||||||||||||
|
|
||||||||||||
| Returns an array `s` that contains the list of singular values of matrix `a`. | ||||||||||||
| If requested, returns a rank-2 array `u` that contains the left singular vectors of `a` along its columns. | ||||||||||||
| If requested, returns a rank-2 array `vt` that contains the right singular vectors of `a` along its rows. | ||||||||||||
|
|
||||||||||||
| Raises `LINALG_ERROR` if the underlying Singular Value Decomposition process did not converge. | ||||||||||||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. What is the value if there is no issue? |
||||||||||||
| Raises `LINALG_VALUE_ERROR` if the matrix or any of the output arrays invalid/incompatible sizes. | ||||||||||||
| Exceptions trigger an `error stop`, unless argument `err` is present. | ||||||||||||
|
|
||||||||||||
| ### Example | ||||||||||||
|
|
||||||||||||
| ```fortran | ||||||||||||
| {!example/linalg/example_svd.f90!} | ||||||||||||
| ``` | ||||||||||||
|
|
||||||||||||
| ## `svdvals` - Compute the singular values of a rank-2 array (matrix). | ||||||||||||
|
|
||||||||||||
| ### Status | ||||||||||||
|
|
||||||||||||
| Experimental | ||||||||||||
|
|
||||||||||||
| ### Description | ||||||||||||
|
|
||||||||||||
| This subroutine computes the singular values of a `real` or `complex` rank-2 array (matrix) from its singular | ||||||||||||
| value decomposition \( A = U \cdot S \cdot \V^T \). The solver is based on LAPACK's `*GESDD` backends. | ||||||||||||
|
|
||||||||||||
| Result vector `s` returns the array of singular values on the diagonal of \( S \). | ||||||||||||
|
|
||||||||||||
| ### Syntax | ||||||||||||
|
|
||||||||||||
| `s = ` [[stdlib_linalg(module):svdvals(interface)]] `(a [, err])` | ||||||||||||
|
|
||||||||||||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
|
||||||||||||
| ### Arguments | ||||||||||||
|
|
||||||||||||
| `a`: Shall be a rank-2 `real` or `complex` array containing the coefficient matrix of size `[m,n]`. It is an `intent(in)` argument. | ||||||||||||
|
|
||||||||||||
| `err` (optional): Shall be a `type(linalg_state_type)` value. This is an `intent(out)` argument. | ||||||||||||
|
|
||||||||||||
| ### Return values | ||||||||||||
|
|
||||||||||||
| Returns an array `s` that contains the list of singular values of matrix `a`. | ||||||||||||
|
|
||||||||||||
| Raises `LINALG_ERROR` if the underlying Singular Value Decomposition process did not converge. | ||||||||||||
| Raises `LINALG_VALUE_ERROR` if the matrix or any of the output arrays invalid/incompatible sizes. | ||||||||||||
| Exceptions trigger an `error stop`, unless argument `err` is present. | ||||||||||||
|
|
||||||||||||
| ### Example | ||||||||||||
|
|
||||||||||||
| ```fortran | ||||||||||||
| {!example/linalg/example_svdvals.f90!} | ||||||||||||
| ``` | ||||||||||||
|
|
||||||||||||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,50 @@ | ||
| ! Singular Value Decomposition | ||
| program example_svd | ||
| use stdlib_linalg_constants, only: dp | ||
| use stdlib_linalg, only: svd | ||
| implicit none | ||
|
|
||
| real(dp), allocatable :: A(:,:),s(:),u(:,:),vt(:,:) | ||
| character(*), parameter :: fmt = "(a,*(1x,f12.8))" | ||
|
|
||
| ! We want to find the singular value decomposition of matrix: | ||
| ! | ||
| ! A = [ 3 2 2] | ||
| ! [ 2 3 -2] | ||
| ! | ||
| A = transpose(reshape([ 3, 2, 2, & | ||
| 2, 3,-2], [3,2])) | ||
|
|
||
| ! Prepare arrays | ||
| allocate(s(2),u(2,2),vt(3,3)) | ||
|
|
||
| ! Get singular value decomposition | ||
| call svd(A,s,u,vt) | ||
|
|
||
| ! Singular values: [5, 3] | ||
| print fmt, ' ' | ||
| print fmt, 'S = ',s | ||
| print fmt, ' ' | ||
|
|
||
| ! Left vectors (may be flipped): | ||
| ! [�2/2 �2/2] | ||
| ! U = [�2/2 -�2/2] | ||
| ! | ||
| print fmt, ' ' | ||
| print fmt, 'U = ',u(1,:) | ||
| print fmt, ' ',u(2,:) | ||
|
|
||
|
|
||
| ! Right vectors (may be flipped): | ||
| ! [�2/2 �2/2 0] | ||
| ! V = [1/�18 -1/�18 4/�18] | ||
| ! [ 2/3 -2/3 -1/3] | ||
| ! | ||
| print fmt, ' ' | ||
| print fmt, ' ',vt(1,:) | ||
| print fmt, 'VT= ',vt(2,:) | ||
| print fmt, ' ',vt(3,:) | ||
| print fmt, ' ' | ||
|
|
||
|
|
||
| end program example_svd |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,26 @@ | ||
| ! Singular Values | ||
| program example_svdvals | ||
| use stdlib_linalg_constants, only: dp | ||
| use stdlib_linalg, only: svdvals | ||
| implicit none | ||
|
|
||
| real(dp), allocatable :: A(:,:),s(:) | ||
| character(*), parameter :: fmt="(a,*(1x,f12.8))" | ||
|
|
||
| ! We want to find the singular values of matrix: | ||
| ! | ||
| ! A = [ 3 2 2] | ||
| ! [ 2 3 -2] | ||
| ! | ||
| A = transpose(reshape([ 3, 2, 2, & | ||
| 2, 3,-2], [3,2])) | ||
|
|
||
| ! Get singular values | ||
| s = svdvals(A) | ||
|
|
||
| ! Singular values: [5, 3] | ||
| print fmt, ' ' | ||
| print fmt, 'S = ',s | ||
| print fmt, ' ' | ||
|
|
||
| end program example_svdvals |
Uh oh!
There was an error while loading. Please reload this page.