Eigenvalue Problem Solvers
LS.solve(prob, alg; kwargs) for an EigenvalueProblem.
Solves for the eigenpairs $(\lambda, v)$ of $Av = \lambda v$ (or the generalized problem $Av = \lambda Bv$ when a second operator is supplied) defined by prob using the algorithm alg. If no algorithm is given, DenseEigen() is used.
Recommended Methods
The default DenseEigen() wraps LinearAlgebra.eigen and is the right choice for small to moderately sized dense matrices, or whenever most/all of the spectrum is needed. It always computes the full dense eigendecomposition before selecting the requested eigenpairs, so its cost does not depend on num_eigenpairs.
For large sparse or structured matrices where only a handful of eigenpairs are needed, an iterative Krylov-based backend is preferred, since these only ever factorize/apply A (and B) and never form the dense decomposition:
KrylovKitEigen()is a solid default iterative choice: it supports both standard and generalized problems, extremal targets, and interior (shift) targets.ArpackJL()is a mature, widely-used implicitly restarted Arnoldi/Lanczos solver, also supporting extremal and shifted targets on standard and generalized problems.LS.ArnoldiMethod()is a pure-Julia implicitly restarted Arnoldi method. It has no directEigenvalueTarget.SmallestMagnitudesupport; useshift(shift-and-invert) or another backend for interior/smallest eigenvalues instead.JacobiDavidsonJL()is a target/interior method: it is most effective when ashiftclose to the desired eigenvalues is known. It does not support generalized eigenvalue problems.
Full List of Methods
LinearAlgebra (built-in)
LinearSolve.AbstractEigenvalueAlgorithm — Type
AbstractEigenvalueAlgorithmBase type for algorithms that solve an EigenvalueProblem. An instance is passed as the second argument of solve(prob::EigenvalueProblem, alg); when no algorithm is given, DenseEigen() is used.
The concrete algorithms are:
DenseEigen: denseLinearAlgebra.eigen, the default; always available.ArpackJL:Arpack.eigs(requiresusing Arpack).ArnoldiMethodJL/ArnoldiMethod:ArnoldiMethod.partialschur(requiresusing ArnoldiMethod).KrylovKitEigen:KrylovKit.eigsolve(requiresusing KrylovKit).JacobiDavidsonJL:JacobiDavidson.jdqr(requiresusing JacobiDavidson).
A new backend subtypes this type and defines SciMLBase.solve(prob::EigenvalueProblem, alg::MyAlg, args...; kwargs...), returning an EigenvalueSolution (see SciMLBase.build_eigenvalue_solution). The fallback method for the abstract type throws "The eigenvalue backend ... is not available", which is what a user sees when an extension-backed algorithm is used before its package has been loaded.
LinearSolve.DenseEigen — Type
DenseEigen()Solve the EigenvalueProblem with LinearAlgebra.eigen. This is the default algorithm: it computes the full dense eigendecomposition and then selects the requested eigenpairs (via num_eigenpairs, eigentarget, or shift) from it. Best for small to moderately sized dense matrices where every eigenpair (or a sizable fraction of them) is needed.
Arpack.jl
LinearSolve.ArpackJL — Type
ArpackJL(; kwargs...)Solve the EigenvalueProblem with Arpack.jl's eigs, an iterative Krylov (implicitly restarted Arnoldi/Lanczos) solver well suited to computing a handful of extremal eigenpairs of a large sparse or structured matrix. Extra kwargs are forwarded to Arpack.eigs.
ArnoldiMethod.jl
LinearSolve.ArnoldiMethod — Function
ArnoldiMethod(; kwargs...)Solve the EigenvalueProblem with ArnoldiMethod.jl's partialschur, a pure-Julia implicitly restarted Arnoldi method for large sparse or structured matrices. Extra kwargs are forwarded to ArnoldiMethod.partialschur.
Restrictions of the backend:
- Standard problems only: a generalized problem (
B !== nothing) raises an error. eigentarget = EigenvalueTarget.SmallestMagnitudeis not supported directly; supplyshiftfor shift-and-invert instead, or use another backend such asKrylovKitEigen()orArpackJL().
This constructor returns an ArnoldiMethodJL; the two names build the same algorithm. Once the ArnoldiMethod.jl package is loaded the bare name ArnoldiMethod refers to that module, so use ArnoldiMethodJL(; kwargs...) (or LinearSolve.ArnoldiMethod) in that case.
LinearSolve.ArnoldiMethodJL — Type
ArnoldiMethodJL(; kwargs...)Solve the EigenvalueProblem with ArnoldiMethod.jl's partialschur, a pure-Julia implicitly restarted Arnoldi method for computing a few eigenpairs of a large sparse or structured matrix. Extra kwargs are forwarded to ArnoldiMethod.partialschur (for example tol, mindim, maxdim, restarts).
Restrictions of the backend:
- Standard problems only: a generalized problem (
B !== nothing) raises an error. eigentarget = EigenvalueTarget.SmallestMagnitudeis not supported directly (ArnoldiMethod has no such target); supplyshiftfor shift-and-invert, which factorizesA - shift*Iand finds the eigenvalues nearestshift, or use another backend such asKrylovKitEigen()orArpackJL().
ArnoldiMethodJL(; kwargs...) and ArnoldiMethod(; kwargs...) build the same algorithm object; this is the spelling to prefer once the ArnoldiMethod.jl package is loaded. Loading that package is what makes the solver available, and it binds the name ArnoldiMethod to the module, so after using LinearSolve, ArnoldiMethod a bare ArnoldiMethod(; kwargs...) reaches the module rather than the constructor and fails with "objects of type Module are not callable" (and ?ArnoldiMethod shows the module's help). ArnoldiMethodJL does not collide, and matches how the other backends are named.
KrylovKit.jl
LinearSolve.KrylovKitEigen — Type
KrylovKitEigen(; kwargs...)Solve the EigenvalueProblem with KrylovKit.jl's eigsolve, a Krylov solver for a few extremal or interior (shifted) eigenpairs of a large sparse or structured matrix. Extra kwargs are forwarded to the KrylovKit call (for example tol, krylovdim, maxiter, issymmetric, ishermitian, isposdef).
Which KrylovKit routine runs depends on the problem:
- Standard problem, no
shift:KrylovKit.eigsolve(A, nev, which)withwhichderived fromeigentarget; no symmetry or definiteness is required ofA. - Any problem with a
shift: shift-and-invert.A - shift*I(orA - shift*Bfor a generalized problem) is factorized andKrylovKit.eigsolveis run on the inverse operator, so general (non-Hermitian) pencils are supported on this path. - Generalized problem without a
shift:KrylovKit.geneigsolve((A, B), nev, which). KrylovKit only implements the symmetric/Hermitian case with positive definiteBand throws anArgumentErrorotherwise (it also rejects the imaginary-part targets). For matrices these properties are detected automatically; for other operator types passissymmetric = true/ishermitian = trueandisposdef = truethroughkwargs. For a non-Hermitian pencil supply ashiftinstead.
JacobiDavidson.jl
LinearSolve.JacobiDavidsonJL — Type
JacobiDavidsonJL(; kwargs...)Solve the EigenvalueProblem with JacobiDavidson.jl's jdqr, a target/interior method that finds the eigenvalues nearest a given shift. Does not support generalized eigenvalue problems (upstream jdqz is broken). Extra kwargs are forwarded to JacobiDavidson.jdqr.