Hi,
The following code involves a swap operation between particles of two regions R1, R3. I am trying to implement Eq. 5 (https://journals.aps.org/prb/abstract/10.1103/PhysRevB.103.075102) in which V, W are defined in Eq. 10. By setting the angle to 0 in the code, one effectively just performs the swap operation S.
I used the ground state of the hofstadter model(Eq. 79) for a 5x6 system. However, the code gave an out of memory error even with a random mps. The linkdims of random_mps() is changed to match values for the hofstadter model(It was noted that having a linkdims around 250 leads to the error). Reducing the linkdims leads to poor results for the eigenspectrum when implementing the hofstadter model.
struct Region_parameters
Nx::Int
Ny::Int
R1_x_from::Int
R1_x_to::Int
R2_x_from::Int
R2_x_to::Int
R3_x_from::Int
R3_x_to::Int
y_from::Int
y_to::Int
end
function xy_to_label(x, y, Nx, Ny)
return Ny*(x-1) + (y)
end
#Define the number operator for the S=1/2 site.
ITensors.op(::OpName"N",::SiteType"S=1/2")=
[0.75 0
0 0.25]
function swap_one_copy(Rp::Region_parameters, sites::Any, psi::MPS, theta::Float64, prefactor::Any)
N = length(psi)
L = Rp.R3_x_from - Rp.R1_x_from
#REGION 1
x = Rp.R1_x_from
y = 1
p = xy_to_label(x, y, Rp.Nx, Rp.Ny)
pL = xy_to_label(x + L, y, Rp.Nx, Rp.Ny)
angle=0
T1=psi[p]
T1*=exp(1im*angle*op(sites, "N", p))
T1*=delta(prime(dag(sites[p])), sites[pL])
T1*=dag(prime(psi[pL], "Link"))
for y in 2:(Rp.Ny)
p=xy_to_label(x, y, Rp.Nx, Rp.Ny)
pL=xy_to_label(x+L, y, Rp.Nx, Rp.Ny)
angle=0
T1*=psi[p]
T1*=exp(1im*angle*op(sites, "N", p))
T1*=delta(prime(dag(sites[p])), sites[pL])
T1*=dag(prime(psi[pL], "Link"))
end
for x in (Rp.R1_x_from+1):Rp.R1_x_to
for y in 1:(Rp.Ny)
p=xy_to_label(x, y, Rp.Nx, Rp.Ny)
pL=xy_to_label(x+L, y, Rp.Nx, Rp.Ny)
angle=0
T1*=psi[p]
T1*=exp(1im*angle*op(sites, "N", p))
T1*=delta(prime(dag(sites[p])), sites[pL])
T1*=dag(prime(psi[pL], "Link"))
end
end
#REGION 2
x = Rp.R2_x_from
y = 1
p = xy_to_label(x, y, Rp.Nx, Rp.Ny)
angle=0
T2=psi[p]
T2*=exp(1im*angle*op(sites, "N", p))
T2*=dag(prime(psi[p]))
for y in 2:(Rp.Ny)
p = xy_to_label(x, y, Rp.Nx, Rp.Ny)
angle=0
T2*=psi[p]
T2*=exp(1im*angle*op(sites, "N", p))
T2*=dag(prime(psi[p]))
end
for x in (Rp.R2_x_from+1):Rp.R2_x_to
for y=1: (Rp.Ny)
p=xy_to_label(x, y, Rp.Nx, Rp.Ny)
angle=0
T2*=psi[p]
T2*=exp(1im*angle*op(sites, "N", p))
T2*=dag(prime(psi[p]))
end
end
#REGION 3
x = Rp.R3_x_from
y = 1
p = xy_to_label(x, y, Rp.Nx, Rp.Ny)
pL = xy_to_label(x-L, y, Rp.Nx, Rp.Ny)
angle=0
T3=psi[p]
T3*=exp(1im*angle*op(sites, "N", p))
T3*=delta(prime(dag(sites[p])), sites[pL])
T3*=dag(prime(psi[pL], "Link"))
for y in 2:(Rp.Ny)
p=xy_to_label(x, y, Rp.Nx, Rp.Ny)
pL=xy_to_label(x-L, y, Rp.Nx, Rp.Ny)
angle=0
T3*=psi[p]
T3*=exp(1im*angle*op(sites, "N", p))
T3*=delta(prime(dag(sites[p])), sites[pL])
T3*=dag(prime(psi[pL], "Link"))
end
for x in (Rp.R3_x_from+1):Rp.R3_x_to
for y in 1:(Rp.Ny)
p=xy_to_label(x, y, Rp.Nx, Rp.Ny)
pL=xy_to_label(x-L, y, Rp.Nx, Rp.Ny)
angle=0
T3*=psi[p]
T3*=exp(1im*angle*op(sites, "N", p))
T3*=delta(prime(dag(sites[p])), sites[pL])
T3*=dag(prime(psi[pL], "Link"))
end
end
T=T1*T2*T3
Ledge = xy_to_label(Rp.R1_x_from, 1, Rp.Nx, Rp.Ny)-1
Redge = xy_to_label(Rp.R3_x_to, Rp.Ny, Rp.Nx, Rp.Ny)+1
for i in Ledge:-1:1
T*=psi[i]
T*=dag(prime(psi[i], "Link"))
end
for i in Redge:N
T*=psi[i]
T*=dag(prime(psi[i], "Link"))
end
return complex(T)
end
Nx=5
Ny=6
N=Nx*Ny
Rp = Region_parameters(Nx,Ny,1,2,3,3,4,5,1,6)
sites_spin=siteinds("S=1/2", N; conserve_qns=true)
init_state=[isodd(n) ? "Up" : "Dn" for n in 1:N]
psi_GS=random_mps(sites_spin, init_state, linkdims=250)
tensor=swap_one_copy(Rp, sites_spin, psi_GS, 0.1, 1.0)
Here are my doubts-
- Is there anything important to keep in mind when implementing swap operations?
- I wonder if my implementation is responsible for leading to the out of memory error. Or is it the value of linkdims?
Any inputs about improving the code will be helpful. Thanks!