Open HamidArianZad opened 8 months ago
Hi Hamid,
The object Operator
currently is not an AbstractMatrix
. It can multiply to a vector, though. So for the Lanczos algorithm, the way to go is to use the method
eigsolve(f, x₀, [howmany = 1, which = :LM]; kwargs...)
Here, the first argument can be the multiplication function x -> H * x
.
Dear Jie,
I performed
x₀ = ones(size(H, 1))
energy = eigsolve(x -> H * x, x₀, howmany=1, which=:LM)
But still get following error
ERROR: LoadError: MethodError: no method matching eigselector(::var"#3#7"{EDKit.Operator{Float64, TranslationalBasis{Int64, Float64}}}, ::Type{Float64}; howmany::Int64, which::Symbol)
Closest candidates are:
eigselector(::Any, ::Type; issymmetric, ishermitian, krylovdim, maxiter, tol, orth, eager, verbosity) got unsupported keyword arguments "howmany", "which"
@ KrylovKit ~/.julia/packages/KrylovKit/diNbc/src/eigsolve/eigsolve.jl:205
eigselector(::AbstractMatrix, ::Type; issymmetric, ishermitian, krylovdim, maxiter, tol, orth, eager, verbosity) got unsupported keyword arguments "howmany", "which"
@ KrylovKit ~/.julia/packages/KrylovKit/diNbc/src/eigsolve/eigsolve.jl:237
Hi Hamid, The "howmany" and "which" are not keyword argument, you can try removing the argument names in the eigsolve function.
Thank you for your response,
Term energy = eigsolve(x -> Array(H) * x, x₀)
still does not work, and I get similar error. Please know that I need to limit the number of eigenvalues to smaller values compared to the hole spectrum specifically for 18 number of spins.
So, the term howmany
may play important role.
I used the alternative term Arpack.eigs
:
if i <= 3
energy = eigvals(Hermitian(H))
else
# x₀ = ones(size(H, 1))
# energy = eigsolve(x -> Array(H) * x, x₀)
# energy = eigsolve(x -> H * x, x₀)
energy = Arpack.eigs(Array(H), nev=100, which=:LM, tol=1e-8)
end
Arpack.eigs
seems work, but it always returns 6 eigenvalues. I tried other option: which=:SR
, but Arpack.eigs
does not give more than 6 eigenvalues.
Sorry for the confusion. What I mean is
energy = eigsolve(x -> H * x, x₀, 1, :LM)
That is the usage of eigsolve
in KrylovKit
when the first argument is a function.
Besides, when H is getting large, you can also consider using sparse(H)
to get a sparse matrix of the Hamiltonian (and for that purpose you need to import SparseArrays
). Using Array(H)
is not very efficient in this case.
I tried what you suggested:
x₀ = ones(size(H, 1))
energy = eigsolve(x -> H * x, x₀, 1, :SR)
still I get error:
ERROR: LoadError: MethodError: no method matching iterate(::KrylovKit.ConvergenceInfo{Vector{Float64}, Vector{Vector{ComplexF64}}})
Closest candidates are:
iterate(::KrylovKit.SplitRange)
@ KrylovKit ~/.julia/packages/KrylovKit/diNbc/src/KrylovKit.jl:83
iterate(::KrylovKit.SplitRange, ::Any)
@ KrylovKit ~/.julia/packages/KrylovKit/diNbc/src/KrylovKit.jl:83
iterate(::Core.MethodMatch, ::Int64)
@ Base deprecated.jl:265
I also considered x = ones(size(H, 1))
, but it did not help to solve the problem.
btw, when I consider sparse(H)
I get following error from line if i <= 3 energy = eigvals(sparse(H))
:
ERROR: LoadError: MethodError: no method matching eigvals!(::SparseMatrixCSC{Float64, Int64})
Closest candidates are:
eigvals!(::AbstractMatrix{T}, ::Cholesky{T}; sortby) where T<:Number
@ LinearAlgebra /snap/julia/92/share/julia/stdlib/v1.10/LinearAlgebra/src/symmetriceigen.jl:217
eigvals!(::SymTridiagonal{<:Union{Float32, Float64}, <:StridedVector{T} where T})
@ LinearAlgebra /snap/julia/92/share/julia/stdlib/v1.10/LinearAlgebra/src/tridiag.jl:265
eigvals!(::SymTridiagonal{<:Union{Float32, Float64}, <:StridedVector{T} where T}, ::UnitRange)
@ LinearAlgebra /snap/julia/92/share/julia/stdlib/v1.10/LinearAlgebra/src/tridiag.jl:268
...
Well it is a bit strange. On my computer, for i=7
, eigsolve(x -> H * x, x₀, 1, :SR)
works fine.
Anyway for Lanczos problem, you can alway convert the Hamiltonian to sparse matrix and then use the Arpack to solve the eigenvalues.
eigs(sparse(H), nev = 20, which=:SR)
As for your second error message. It is just because eigvals
function does not work for sparse matrices. So for the complete diagonalization case, you don need to convert H
to a sparse matrix.
Thank you very much for your assistance.
The command energy, _ = eigs(sparse(H), nev = 20, which=:SR)
works well for system with N <= 12.
However, when I attempted to diagonalize the Hamiltonian for the 18-spin system, I encountered a memory error. This happened even when I reduced nev
to 1, indicating that the memory issue persists regardless of the number of desired eigenvalues.
The error occurs specifically at i = 7
for the 18-spin system, leading to the termination of the diagonalization process. This is unexpected as I am operating on a PC with 64 gig of RAM.
I had the same issue when I tried to use ED method to diagonalize the spin-1 system with N = 18
using ITensor.jl.
I am not sure that whether HPhi can do diagonalization for 18-spin system using Lanczos algorithm on my PC.
I would greatly appreciate it if you could provide any insights or suggestions regarding this memory issue. Perhaps there are alternative approaches or optimizations that could be applied by EDKit to address this challenge.
Dear Jie,
Thank you for your excellent package.
I have successfully solved the problem with a spin-1 diamond chain up to 12 spins. Now, I aim to increase the number of spins to 18 while conserving SzT by applying TranslationalBasis. I have 64 GB of RAM, and the code gets terminated when the total Sz exceeds sector 6. To address this issue, I need to utilize the Lanczos algorithm. Here is the code I have managed:
But I get following error:
It seems that
eigsolve
is unable to recognize the Hamiltonian matrix, whether it's the full Hamiltonian or the reduced Hamiltonian after applyingTranslationalBasis
.I would appreciate your comments and suggestions on this issue.