Skip to content

Commit f6554f3

Browse files
committed
Neighbourhood tensor update
1 parent 0c74c01 commit f6554f3

6 files changed

Lines changed: 778 additions & 11 deletions

File tree

src/PEPSKit.jl

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -89,6 +89,7 @@ include("algorithms/contractions/bp_contractions.jl")
8989
include("algorithms/contractions/bondenv/benv_tools.jl")
9090
include("algorithms/contractions/bondenv/gaugefix.jl")
9191
include("algorithms/contractions/bondenv/als_solve.jl")
92+
include("algorithms/contractions/bondenv/benv_ntu.jl")
9293
include("algorithms/contractions/bondenv/benv_ctm.jl")
9394
include("algorithms/contractions/correlator/peps.jl")
9495
include("algorithms/contractions/correlator/pepo_1layer.jl")
@@ -111,6 +112,8 @@ include("algorithms/time_evolution/apply_mpo.jl")
111112
include("algorithms/time_evolution/time_evolve.jl")
112113
include("algorithms/time_evolution/simpleupdate.jl")
113114
include("algorithms/time_evolution/simpleupdate3site.jl")
115+
include("algorithms/time_evolution/ntupdate.jl")
116+
include("algorithms/time_evolution/ntupdate3site.jl")
114117
include("algorithms/time_evolution/gaugefix_su.jl")
115118

116119
include("algorithms/bp/beliefpropagation.jl")
@@ -143,14 +146,16 @@ export fixedpoint
143146

144147
export absorb_weight
145148
export ALSTruncation, FullEnvTruncation
146-
export SimpleUpdate
149+
export NNEnv, NNpEnv, NNNEnv
150+
export SimpleUpdate, NeighbourUpdate
147151
export TimeEvolver, timestep, time_evolve
148152

149153
export InfiniteSquareNetwork
150154
export InfinitePartitionFunction
151155
export InfinitePEPS, InfiniteTransferPEPS
152156
export SUWeight
153157
export InfinitePEPO, InfiniteTransferPEPO
158+
export infinite_temperature_density_matrix
154159

155160
export BPEnv, BeliefPropagation
156161
export BPGauge, SUGauge
Lines changed: 239 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,239 @@
1+
#=
2+
The construction of bond environment for Neighborhood Tensor Update (NTU)
3+
is adapted from YASTN (https://github.com/yastn/yastn).
4+
Copyright 2024 The YASTN Authors. All Rights Reserved.
5+
Licensed under the Apache License, Version 2.0
6+
=#
7+
8+
"""
9+
Algorithms to construct bond environment for Neighborhood Tensor Update (NTU).
10+
"""
11+
abstract type NeighbourEnv end
12+
13+
"""
14+
SVD with `truncrank(1)`.
15+
"""
16+
function _svd_cut!(t::AbstractTensorMap)
17+
t1, s, t2 = svd_trunc!(t; trunc = truncrank(1))
18+
return absorb_s(t1, s, t2)
19+
end
20+
21+
"""
22+
Algorithm struct for "NTU-NN" bond environment.
23+
"""
24+
struct NNEnv <: NeighbourEnv end
25+
"""
26+
Calculate the bond environment within "NTU-NN" approximation.
27+
```
28+
-1 ●=======●
29+
║ ║
30+
0 ●===X== ==Y===●
31+
║ ║
32+
1 ●=======●
33+
-1 0 1 2
34+
```
35+
"""
36+
function bondenv_ntu(
37+
row::Int, col::Int, X::T, Y::T, state::S, alg::NNEnv
38+
) where {T, S <: InfiniteState}
39+
neighbors = [(-1, 0), (0, -1), (1, 0), (1, 1), (0, 2), (-1, 1)]
40+
m = collect_neighbors(state, row, col, neighbors)
41+
X, Y = _prepare_site_tensor(X), _prepare_site_tensor(Y)
42+
# southwest half
43+
@autoopt @tensor benv_sw[Dse1 Dse0 Dw1 Dw0 Dnw1 Dnw0] :=
44+
cor_se(m[1, 1])[Dse1 Dse0 Ds1 Ds0] *
45+
cor_sw(m[1, 0])[Dsw1 Dsw0 Ds1 Ds0] *
46+
edge_w(X, hair_w(m[0, -1]))[Dnw1 Dnw0 Dw1 Dw0 Dsw1 Dsw0]
47+
normalize!(benv_sw, Inf)
48+
# northeast half
49+
@autoopt @tensor benv_ne[Dnw1 Dnw0 De1 De0 Dse1 Dse0] :=
50+
cor_nw(m[-1, 0])[Dn1 Dn0 Dnw1 Dnw0] *
51+
cor_ne(m[-1, 1])[Dne1 Dne0 Dn1 Dn0] *
52+
edge_e(Y, hair_e(m[0, 2]))[Dne1 Dne0 Dse1 Dse0 De1 De0]
53+
normalize!(benv_ne, Inf)
54+
@tensor benv[Dw1 De1; Dw0 De0] :=
55+
benv_sw[Dse1 Dse0 Dw1 Dw0 Dnw1 Dnw0] * benv_ne[Dnw1 Dnw0 De1 De0 Dse1 Dse0]
56+
normalize!(benv, Inf)
57+
return benv
58+
end
59+
60+
"""
61+
Algorithm struct for "NTU-NN+" bond environment.
62+
"""
63+
struct NNpEnv <: NeighbourEnv end
64+
"""
65+
Calculate the bond environment within "NTU-NN+" approximation.
66+
```
67+
-2 ●.......●
68+
║ ║
69+
-1 ○===●=======●===○
70+
║ ║ ║ ║
71+
0 ●===●===X== ==Y===●===●
72+
║ ║ ║ ║
73+
1 ○===●=======●===○
74+
║ ║
75+
2 ●.......●
76+
-2 -1 0 1 2 3
77+
```
78+
Dotted lines and ○ are splitted using SVD with `truncrank(1)`.
79+
"""
80+
function bondenv_ntu(
81+
row::Int, col::Int, X::T, Y::T, state::S, alg::NNpEnv
82+
) where {T, S <: InfiniteState}
83+
neighbors = [
84+
(-1, -1), (0, -1), (1, -1), (1, 0), (1, 1), (1, 2), (0, 2), (-1, 2),
85+
(-1, 1), (-1, 0), (0, -2), (2, 0), (2, 1), (0, 3), (-2, 1), (-2, 0),
86+
]
87+
ms = collect_neighbors(state, row, col, neighbors)
88+
X, Y = _prepare_site_tensor(X), _prepare_site_tensor(Y)
89+
90+
# ---- hairs (size D^2) with a 1D auxiliary leg ----
91+
92+
@tensor top[-1 -2; -3 -4] := cor_nw(ms[-2, 0])[1 2 -1 -2] * cor_ne(ms[-2, 1])[-3 -4 1 2]
93+
tl, tr = _svd_cut!(top)
94+
95+
@tensor bot[-1 -2; -3 -4] := cor_sw(ms[2, 0])[-1 -2 1 2] * cor_se(ms[2, 1])[-3 -4 1 2]
96+
bl, br = _svd_cut!(bot)
97+
98+
nw = permute(cor_nw(ms[-1, -1]), ((3, 4), (1, 2)))
99+
nw1, nw2 = _svd_cut!(nw)
100+
101+
ne = permute(cor_ne(ms[-1, 2]), ((3, 4), (1, 2)))
102+
ne1, ne2 = _svd_cut!(ne)
103+
104+
sw = permute(cor_sw(ms[1, -1]), ((1, 2), (3, 4)))
105+
sw1, sw2 = _svd_cut!(sw)
106+
107+
se = permute(cor_se(ms[1, 2]), ((3, 4), (1, 2)))
108+
se1, se2 = _svd_cut!(se)
109+
110+
m = ms[0, -1]
111+
@tensoropt hW[anw DXw1 DXw0 asw] :=
112+
hair_w(ms[0, -2])[Dw21 Dw20] *
113+
nw1[Dnw11 Dnw10 anw] * sw1[Dsw11 Dsw10 asw] *
114+
twistdual(m, 1)[p Dnw10 DXw0 Dsw10 Dw20] *
115+
conj(m[p Dnw11 DXw1 Dsw11 Dw21])
116+
117+
m = ms[0, 2]
118+
@tensoropt hE[ane DYe1 DYe0 ase] :=
119+
hair_e(ms[0, 3])[De21 De20] *
120+
ne2[ane Dne21 Dne20] * se2[ase Dse21 Dse20] *
121+
twistdual(m, 1)[p Dne20 De20 Dse20 DYe0] *
122+
conj(m[p Dne21 De21 Dse21 DYe1])
123+
124+
# ---- corners (size D^4) with a 1D auxiliary leg ----
125+
126+
m = ms[-1, 0]
127+
@tensoropt NW[at Dn1 Dn0 DXn1 DXn0 anw] :=
128+
tl[Dtl1 Dtl0 at] * nw2[anw Dnw21 Dnw20] *
129+
twistdual(m, 1)[p Dtl0 Dn0 DXn0 Dnw20] *
130+
conj(m[p Dtl1 Dn1 DXn1 Dnw21])
131+
132+
m = ms[-1, 1]
133+
@tensoropt NE[at Dn1 Dn0 DYn1 DYn0 ane] :=
134+
tr[at Dtr1 Dtr0] * ne1[Dne11 Dne10 ane] *
135+
twistdual(m, 1)[p Dtr0 Dne10 DYn0 Dn0] *
136+
conj(m[p Dtr1 Dne11 DYn1 Dn1])
137+
138+
m = ms[1, 0]
139+
@tensoropt SW[asw DXs1 DXs0 Ds1 Ds0 ab] :=
140+
bl[Dbl1 Dbl0 ab] * sw2[asw Dsw21 Dsw20] *
141+
twistdual(m, 1)[p DXs0 Ds0 Dbl0 Dsw20] *
142+
conj(m[p DXs1 Ds1 Dbl1 Dsw21])
143+
144+
m = ms[1, 1]
145+
@tensoropt SE[ase DYs1 DYs0 Ds1 Ds0 ab] :=
146+
br[ab Dbr1 Dbr0] * se1[Dse11 Dse10 ase] *
147+
twistdual(m, 1)[p DYs0 Dse10 Dbr0 Ds0] *
148+
conj(m[p DYs1 Dse11 Dbr1 Ds1])
149+
150+
# ---- left half ----
151+
@tensoropt benvL[at Dn1 Dn0 Dw1 Dw0 Ds1 Ds0 ab] :=
152+
hW[anw DXw1 DXw0 asw] *
153+
NW[at Dn1 Dn0 DXn1 DXn0 anw] *
154+
SW[asw DXs1 DXs0 Ds1 Ds0 ab] *
155+
twistdual(X, 1)[p DXn0 Dw0 DXs0 DXw0] *
156+
conj(X[p DXn1 Dw1 DXs1 DXw1])
157+
normalize!(benvL, Inf)
158+
159+
# ---- right half ----
160+
161+
@tensoropt benvR[at Dn1 Dn0 De1 De0 Ds1 Ds0 ab] :=
162+
hE[ane DYe1 DYe0 ase] *
163+
NE[at Dn1 Dn0 DYn1 DYn0 ane] *
164+
SE[ase DYs1 DYs0 Ds1 Ds0 ab] *
165+
twistdual(Y, 1)[p DYn0 DYe0 DYs0 De0] *
166+
conj(Y[p DYn1 DYe1 DYs1 De1])
167+
normalize!(benvR, Inf)
168+
169+
# ---- the full NN+ environment ----
170+
171+
@tensor benv[Dw1, De1; Dw0, De0] :=
172+
benvL[at Dn1 Dn0 Dw1 Dw0 Ds1 Ds0 ab] *
173+
benvR[at Dn1 Dn0 De1 De0 Ds1 Ds0 ab]
174+
normalize!(benv, Inf)
175+
return benv
176+
end
177+
178+
"""
179+
Algorithm struct for "NTU-NNN" bond environment.
180+
"""
181+
struct NNNEnv <: NeighbourEnv end
182+
"""
183+
Calculates the bond environment within "NTU-NNN" approximation.
184+
```
185+
-1 ●===●=======●===●
186+
║ ║ ║ ║
187+
0 ●===X== ==Y===●
188+
║ ║ ║ ║
189+
1 ●===●=======●===●
190+
-1 0 1 2
191+
```
192+
"""
193+
function bondenv_ntu(
194+
row::Int, col::Int, X::T, Y::T, state::S, alg::NNNEnv
195+
) where {T, S <: InfiniteState}
196+
neighbors = [
197+
(-1, -1), (0, -1), (1, -1),
198+
(1, 0), (1, 1), (1, 2), (0, 2),
199+
(-1, 2), (-1, 1), (-1, 0),
200+
]
201+
m = collect_neighbors(state, row, col, neighbors)
202+
X, Y = _prepare_site_tensor(X), _prepare_site_tensor(Y)
203+
#= left half
204+
-1 ●======●=== -1/-2
205+
║ ║
206+
0 ●======X=== -3/-4
207+
║ ║
208+
....D1.....D2...
209+
║ ║
210+
1 ●==D3==●=== -5/-6
211+
-1 0
212+
=#
213+
vecl = enlarge_corner_nw(cor_nw(m[-1, -1]), edge_n(m[-1, 0]), edge_w(m[0, -1]), X)
214+
@tensor vecl[:] :=
215+
cor_sw(m[1, -1])[D11 D10 D31 D30] *
216+
edge_s(m[1, 0])[D21 D20 -5 -6 D31 D30] *
217+
vecl[D11 D10 D21 D20 -1 -2 -3 -4]
218+
normalize!(vecl, Inf)
219+
#= right half
220+
-1 -1/-2===●==D1==●
221+
║ ║
222+
........D2.....D3...
223+
║ ║
224+
0 -3/-4===Y======●
225+
║ ║
226+
1 -5/-6===●======●
227+
0 1
228+
=#
229+
vecr = enlarge_corner_se(cor_se(m[1, 2]), edge_s(m[1, 1]), edge_e(m[0, 2]), Y)
230+
@tensor vecr[:] :=
231+
edge_n(m[-1, 1])[D11 D10 D21 D20 -1 -2] *
232+
cor_ne(m[-1, 2])[D31 D30 D11 D10] *
233+
vecr[D21 D20 D31 D30 -3 -4 -5 -6]
234+
normalize!(vecr, Inf)
235+
# combine left and right part
236+
@tensor benv[-1 -2; -3 -4] := vecl[1 2 -1 -3 3 4] * vecr[1 2 -2 -4 3 4]
237+
normalize!(benv, Inf)
238+
return benv
239+
end

0 commit comments

Comments
 (0)