QuantumKitHub / MPSKit.jl

A Julia package dedicated to simulating quantum many-body systems using Matrix Product States (MPS)
MIT License
136 stars 30 forks source link

`environments(::WindowMPS,H)` assumes same H for `InfiniteMPS` and `FiniteMPS` #88

Open DaanMaertens opened 11 months ago

DaanMaertens commented 11 months ago

When calling environments on a WindowMPS without specifying the lenvs and renvskwargs it will calculate these with the supplied Hamiltonian. For some cases this will result in an AssertionError: len == length(ham) down the line because at some point an explicit check for MPOHamInfEnv that the length of H and the InfiniteMPS need to be equal, was introduced. For example these cases will result in an error.

Ψ = InfiniteMPS([ℂ^2],[ℂ^2]);
window = WindowMPS(Ψ,20);
nn = TensorMap(rand, ComplexF64, ℂ^2 * ℂ^2, ℂ^2 * ℂ^2);
nn += nn'
H = repeat(MPOHamiltonian(nn),20);
environments(window,H)
Ψl = InfiniteMPS([ℂ^2],[ℂ^2]);
Ψf = FiniteMPS(repeat([ℂ^2],20),repeat([ℂ^2],21))
Ψr = repeat(Ψl,2);
nn = TensorMap(rand, ComplexF64, ℂ^2 * ℂ^2, ℂ^2 * ℂ^2);
nn += nn'
H = repeat(MPOHamiltonian(nn),2);
window2 = WindowMPS(Ψl,Ψf,Ψr);
environments(window,H)

A potential solution would be to make the specification of lenv and renv mandatory or demand separate Hamiltonians for the different parts of the window.

lkdvos commented 11 months ago

I guess that given that the hamiltonian you provide has period 20, it does make sense that it has no way of knowing that you mean for the right part of the window to just repeat a single site, rather than the entire operator. Probably the cleanest way is to just have a WindowMPO as well?

DaanMaertens commented 11 months ago

In the TimeDep branch, the environments function for an Window{HL,H,HR} takes this into account correctly. I wanted to point this issue out because at some point environments on an windowmps did work and now it does not anymore.

DaanMaertens commented 11 months ago

This should be resolved with commit 70e8420. There are now three different ways to construct an environment for a WindowMPS.

  1. environments(::WindowMPS,ham::Union{SparseMPO,MPOHamiltonian,DenseMPO},infham::Union{SparseMPO,MPOHamiltonian,DenseMPO}) Here infham is the Hamiltonian for the (left) infinite part. There is an optional argument to specify a Hamiltonian for the right infinite part (by default this is the same as infham). One can also give the leftenv and righten as keyword arguments.
  2. environments(::WindowMPS,::Union{SparseMPO,MPOHamiltonian,DenseMPO},lenvs::Cache,renvs::Cache) A constructor that takes the left and right environment as non-optional arguments. I defined this for convenience since it can be also be accomplished by the above constructor.
  3. environments(Ψ::WindowMPS,windowH::Window) This requires H to be a window struct and returns accordingly a window{::Cache,::Cache,::Cache}. Keyword arguments for the left and right environment are possible. This method is designed to be used for situations where the environments for the infinite parts are expected to change, like for example in time evolution.
lkdvos commented 11 months ago

I think that I might prefer to only define the last two constructors; the first one is achieved very easily by replacing ham, infham with Window(infham_L, ham, infham_R) .

I would also consider having some way of differentiating between fixed or variable left/right parts, but maybe this is actually better included in the type information of WindowMPS. Somehow WindowMPS, which keeps track of the left and right state, should probably assume that these are variable, as they are part of the state, while having a fixed left/right environment can just as easily be included in the operator/environments, and work with just a FiniteMPS as the state. In any case, I would argue that splitting the two yields the most clarity, and at the very least we could consider doing something like

struct WindowMPS{...,IsVariable} end