import json, math, time from itertools import product import numpy as np def lattice(L): edges=[] for r in range(L): for c in range(L): u=r*L+c if c+1 v for b,(v2,w) in enumerate(und): if v2!=v or w==u: continue rw,cw=xy(w); vout=np.array([cw-cv,rw-rv],float) cross=vin[0]*vout[1]-vin[1]*vout[0] dot=vin.dot(vout) theta=0.5*math.atan2(cross,dot) # edge coupling belongs to the undirected edge kk=K[edges.index(tuple(sorted((u,v))))] T[a,b]=math.tanh(kk)*np.exp(1j*theta) sign,ld=np.linalg.slogdet(np.eye(m,dtype=complex)-T) # For planar ferromagnetic examples this branch is positive real. z=(2.0**(L*L))*np.prod(np.cosh(K))*np.sqrt(sign*np.exp(ld)) return float(np.real_if_close(z).real) def kw_check(): rows=[] for L in (2,3): edges=lattice(L); K=np.array([0.17+0.04*((k%3)-1) for k in range(len(edges))]) states=np.array(list(product((-1,1),repeat=L*L)),dtype=np.int8) z_enum=float(np.exp(np.logaddexp.reduce(sum(K[k]*states[:,u]*states[:,v] for k,(u,v) in enumerate(edges))))) z_kw=kw_partition(L,K) rows.append((L,z_enum,z_kw,abs(z_enum-z_kw)/z_enum)) return rows def train_model(X,I,Q, seed, soft, beta, steps=300, batch=128): import torch torch.manual_seed(seed); np.random.seed(seed) dev='cuda' if torch.cuda.is_available() else 'cpu' try: x=torch.tensor(X); ii=torch.nn.functional.one_hot(torch.tensor(I),X.shape[1]).float(); inp=torch.cat([x,ii],1).to(dev); y=torch.tensor(Q,dtype=torch.float32).to(dev) rng=np.random.default_rng(seed+19); yy=torch.tensor((rng.random(len(Q))