Skip to content

Commit 722f5e0

Browse files
committed
Implement calculation of correlation length
1 parent 09e0ae6 commit 722f5e0

File tree

4 files changed

+261
-0
lines changed

4 files changed

+261
-0
lines changed

varipeps/__init__.py

+1
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
from .global_state import global_state as varipeps_global_state
55

66
from . import contractions
7+
from . import corrlength
78
from . import ctmrg
89
from . import expectation
910
from . import mapping

varipeps/contractions/definitions.py

+94
Original file line numberDiff line numberDiff line change
@@ -1947,5 +1947,99 @@ def _prepare_defs(cls):
19471947
],
19481948
}
19491949

1950+
corrlength_transfer_right: Definition = {
1951+
"tensors": [["tensor", "tensor_conj", "T1", "T3"]],
1952+
"network": [
1953+
[
1954+
(-2, 4, 1, -6, 2), # tensor
1955+
(-3, 5, 1, -7, 3), # tensor_conj
1956+
(-1, 2, 3, -5), # T1
1957+
(-4, -8, 5, 4), # T3
1958+
]
1959+
],
1960+
}
1961+
1962+
corrlength_vector_left: Definition = {
1963+
"tensors": [["C1", "T4", "C4"]],
1964+
"network": [
1965+
[
1966+
(1, -1), # C1
1967+
(2, -3, -2, 1), # T4
1968+
(-4, 2), # C4
1969+
]
1970+
],
1971+
}
1972+
1973+
corrlength_vector_right: Definition = {
1974+
"tensors": [["C2", "T2", "C3"]],
1975+
"network": [
1976+
[
1977+
(-1, 1), # C2
1978+
(-2, -3, 2, 1), # T2
1979+
(-4, 2), # C3
1980+
]
1981+
],
1982+
}
1983+
1984+
corrlength_transfer_bottom: Definition = {
1985+
"tensors": [["tensor", "tensor_conj", "T4", "T2"]],
1986+
"network": [
1987+
[
1988+
(2, -6, 1, 4, -2), # tensor
1989+
(3, -7, 1, 5, -3), # tensor_conj
1990+
(-5, 3, 2, -1), # T4
1991+
(4, 5, -8, -4), # T2
1992+
]
1993+
],
1994+
}
1995+
1996+
corrlength_vector_top: Definition = {
1997+
"tensors": [["C1", "T1", "C2"]],
1998+
"network": [
1999+
[
2000+
(-1, 1), # C1
2001+
(1, -2, -3, 2), # T1
2002+
(2, -4), # C2
2003+
]
2004+
],
2005+
}
2006+
2007+
corrlength_vector_bottom: Definition = {
2008+
"tensors": [["C4", "T3", "C3"]],
2009+
"network": [
2010+
[
2011+
(1, -1), # C4
2012+
(1, 2, -3, -2), # T3
2013+
(2, -4), # C3
2014+
]
2015+
],
2016+
}
2017+
2018+
corrlength_absorb_one_column: Definition = {
2019+
"tensors": [["tensor", "tensor_conj", "T1", "T3"], "vec"],
2020+
"network": [
2021+
[
2022+
(3, 8, 2, -2, 4), # tensor
2023+
(5, 9, 2, -3, 6), # tensor_conj
2024+
(1, 4, 6, -1), # T1
2025+
(7, -4, 9, 8), # T3
2026+
],
2027+
[1, 3, 5, 7], # vec
2028+
],
2029+
}
2030+
2031+
corrlength_absorb_one_row: Definition = {
2032+
"tensors": [["tensor", "tensor_conj", "T4", "T2"], "vec"],
2033+
"network": [
2034+
[
2035+
(4, -2, 2, 8, 3), # tensor
2036+
(6, -3, 2, 9, 5), # tensor_conj
2037+
(-1, 6, 4, 1), # T4
2038+
(8, 9, -4, 7), # T3
2039+
],
2040+
[1, 3, 5, 7], # vec
2041+
],
2042+
}
2043+
19502044

19512045
Definitions._prepare_defs()

varipeps/corrlength/__init__.py

+2
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
from . import corrlength
2+
from .corrlength import calculate_correlation_length

varipeps/corrlength/corrlength.py

+164
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,164 @@
1+
import numpy as np
2+
from scipy.sparse.linalg import LinearOperator, eigs
3+
4+
import jax.numpy as jnp
5+
from jaxlib.xla_extension import XlaRuntimeError
6+
7+
from varipeps.contractions import apply_contraction_jitted
8+
from varipeps.peps import PEPS_Unit_Cell
9+
10+
11+
def calculate_correlation_length(unitcell: PEPS_Unit_Cell):
12+
use_full = True
13+
14+
full_transfer_right = None
15+
full_transfer_bottom = None
16+
17+
try:
18+
for _, view in unitcell.iter_one_row(0):
19+
transfer_right = apply_contraction_jitted(
20+
"corrlength_transfer_right",
21+
(view[0, 0][0][0].tensor,),
22+
(view[0, 0][0][0],),
23+
(),
24+
)
25+
transfer_right = transfer_right.reshape(
26+
np.prod(transfer_right.shape[:4]), np.prod(transfer_right.shape[4:])
27+
)
28+
29+
if full_transfer_right is None:
30+
full_transfer_right = transfer_right
31+
else:
32+
full_transfer_right = full_transfer_right @ transfer_right
33+
34+
initial_vector_right = apply_contraction_jitted(
35+
"corrlength_vector_right",
36+
(unitcell[0, -1][0][0].tensor,),
37+
(view[0, -1][0][0],),
38+
(),
39+
)
40+
initial_vector_right = initial_vector_right.reshape(-1)
41+
42+
for _, view in unitcell.iter_one_column(0):
43+
transfer_bottom = apply_contraction_jitted(
44+
"corrlength_transfer_bottom",
45+
(view[0, 0][0][0].tensor,),
46+
(view[0, 0][0][0],),
47+
(),
48+
)
49+
transfer_bottom = transfer_bottom.reshape(
50+
np.prod(transfer_bottom.shape[:4]), np.prod(transfer_bottom.shape[4:])
51+
)
52+
53+
if full_transfer_bottom is None:
54+
full_transfer_bottom = transfer_bottom
55+
else:
56+
full_transfer_bottom = full_transfer_bottom @ transfer_bottom
57+
58+
initial_vector_bottom = apply_contraction_jitted(
59+
"corrlength_vector_bottom",
60+
(unitcell[-1, 0][0][0].tensor,),
61+
(view[-1, 0][0][0],),
62+
(),
63+
)
64+
initial_vector_bottom = initial_vector_bottom.reshape(-1)
65+
66+
eig_right, eigvec_right = eigs(
67+
full_transfer_right, k=5, v0=initial_vector_right, which="LM"
68+
)
69+
70+
eig_right = np.abs(eig_right)
71+
eig_right /= eig_right[0]
72+
73+
corr_len_right = -1 / np.log(eig_right[1])
74+
75+
eig_bottom, eigvec_bottom = eigs(
76+
full_transfer_bottom, k=5, v0=initial_vector_bottom, which="LM"
77+
)
78+
79+
eig_bottom = np.abs(eig_bottom)
80+
eig_bottom /= eig_bottom[0]
81+
82+
corr_len_bottom = -1 / np.log(eig_bottom[1])
83+
84+
return (corr_len_right, eig_right), (corr_len_bottom, eig_bottom)
85+
except XlaRuntimeError:
86+
initial_vector_left = apply_contraction_jitted(
87+
"corrlength_vector_left",
88+
(unitcell[0, 0][0][0].tensor,),
89+
(view[0, 0][0][0],),
90+
(),
91+
)
92+
initial_vector_left = initial_vector_left.reshape(-1)
93+
94+
initial_vector_top = apply_contraction_jitted(
95+
"corrlength_vector_top",
96+
(unitcell[0, 0][0][0].tensor,),
97+
(view[0, 0][0][0],),
98+
(),
99+
)
100+
initial_vector_top = initial_vector_top.reshape(-1)
101+
102+
def left_matvec(vec):
103+
vec = jnp.asarray(vec)
104+
for _, view in unitcell.iter_one_row(0):
105+
if vec.ndim != 4:
106+
vec = vec.reshape(
107+
view[0, 0][0][0].T1.shape[0],
108+
view[0, 0][0][0].tensor.shape[0],
109+
view[0, 0][0][0].tensor.shape[0],
110+
view[0, 0][0][0].T3.shape[0],
111+
)
112+
vec = apply_contraction_jitted(
113+
"corrlength_absorb_one_column",
114+
(view[0, 0][0][0].tensor,),
115+
(view[0, 0][0][0],),
116+
(vec,),
117+
)
118+
return vec.reshape(-1)
119+
120+
left_lin_op = LinearOperator(
121+
(initial_vector_left.shape[0], initial_vector_left.shape[0]),
122+
matvec=left_matvec,
123+
)
124+
125+
eig_left, eigvec_left = eigs(
126+
left_lin_op, k=5, v0=initial_vector_left, which="LM"
127+
)
128+
129+
eig_left = np.abs(eig_left)
130+
eig_left /= eig_left[0]
131+
132+
corr_len_left = -1 / np.log(eig_left[1])
133+
134+
def top_matvec(vec):
135+
vec = jnp.asarray(vec)
136+
for _, view in unitcell.iter_one_row(0):
137+
if vec.ndim != 4:
138+
vec = vec.reshape(
139+
view[0, 0][0][0].T4.shape[3],
140+
view[0, 0][0][0].tensor.shape[4],
141+
view[0, 0][0][0].tensor.shape[4],
142+
view[0, 0][0][0].T2.shape[3],
143+
)
144+
vec = apply_contraction_jitted(
145+
"corrlength_absorb_one_row",
146+
(view[0, 0][0][0].tensor,),
147+
(view[0, 0][0][0],),
148+
(vec,),
149+
)
150+
return vec.reshape(-1)
151+
152+
top_lin_op = LinearOperator(
153+
(initial_vector_top.shape[0], initial_vector_top.shape[0]),
154+
matvec=top_matvec,
155+
)
156+
157+
eig_top, eigvec_top = eigs(top_lin_op, k=5, v0=initial_vector_top, which="LM")
158+
159+
eig_top = np.abs(eig_top)
160+
eig_top /= eig_top[0]
161+
162+
corr_len_top = -1 / np.log(eig_top[1])
163+
164+
return (corr_len_left, eig_left), (corr_len_top, eig_top)

0 commit comments

Comments
 (0)