def sweep_updateBoundary(dmrg, ncsite, sitelst, qred, srotR, status): if ncsite == 2: if status == 'L' and sitelst[-1] == dmrg.nsite - 1: # >>> Only the gs state is saved for generating MPS. smat = srotR[0] norm = numpy.linalg.norm(smat) if (not dmrg.ifpt) or (dmrg.ifpt and dmrg.ifcompression): smat = smat / norm key = mpo_dmrg_dotutil.floatKey(dmrg.qsectors.keys()[0]) qsym = [numpy.array(eval(key))] if dmrg.ifQt: qtmp = qtensor.qtensor([False, False, True]) qtmp.fromDenseTensor(smat, [qred, dmrg.qphys[dmrg.nsite - 1], qsym]) smat = qtmp # DUMP mpo_dmrg_io.saveQnum(dmrg.flmps, dmrg.nsite, qsym) mpo_dmrg_io.saveSite(dmrg.flmps, dmrg.nsite - 1, smat) elif status == 'R' and sitelst[0] == 0: # >>> Only the gs state is saved for generating MPS. smat = srotR[0] norm = numpy.linalg.norm(smat) if (not dmrg.ifpt) or (dmrg.ifpt and dmrg.ifcompression): smat = smat / norm key = mpo_dmrg_dotutil.floatKey(dmrg.qsectors.keys()[0]) qsym = [numpy.array(eval(key))] if dmrg.ifQt: qtmp = qtensor.qtensor([True, False, False]) qtmp.fromDenseTensor(smat, [qsym, dmrg.qphys[0], qred]) smat = qtmp # DUMP mpo_dmrg_io.saveQnum(dmrg.frmps, 0, qsym) mpo_dmrg_io.saveSite(dmrg.frmps, 0, smat) return 0
def sweep_updateSite(dmrg, isite, ncsite, sigs, qred, site, status): # Update symmetry and save sites if status == 'L': # Example:[==**-] isite=2, lmps[2], qnuml[3] dmrg.sigsl[isite + 1] = sigs.copy() dmrg.qnuml[isite + 1] = qred.copy() if dmrg.ifQt: qtmp = qtensor.qtensor([False, False, True]) # Ql[i-1] + Qn[i] = Ql[i] qtmp.fromDenseTensor(site, [dmrg.qlst[0], dmrg.qlst[1], qred]) siteN = qtmp else: siteN = site.copy() # DUMP mpo_dmrg_io.saveQnum(dmrg.flmps, isite + 1, qred) mpo_dmrg_io.saveSite(dmrg.flmps, isite, siteN) elif status == 'R': # Example: [--**=] isite=2, jsite=3, rmps[3], qnumr[3] jsite = isite + ncsite - 1 dmrg.sigsr[jsite] = sigs.copy() dmrg.qnumr[jsite] = qred.copy() if dmrg.ifQt: qtmp = qtensor.qtensor([True, False, False]) # Qr[i-1] = Qn[i] + Qr[i] qtmp.fromDenseTensor(site, [qred, dmrg.qlst[-2], dmrg.qlst[-1]]) siteN = qtmp else: siteN = site.copy() # DUMP mpo_dmrg_io.saveQnum(dmrg.frmps, jsite, qred) mpo_dmrg_io.saveSite(dmrg.frmps, jsite, siteN) return siteN
def default(self,sc,fmps=None): rank = self.comm.rank self.schedule = sc self.crit_tol = sc.tol if rank == 0: print '\n[mpo_dmrg_class.default]' mpo_dmrg_prt.title(self) ti = time.time() # Count states self.initStates() if rank == 0: # Only set Dcut for rank-0 is sufficient, # as RDM truncation is done here. if self.Dcut is not None: print ' Dcut = ',self.Dcut # Similar to qnuml and qnumr assert len(self.Dcut) == self.nsite-1 self.Dcut = [1]+self.Dcut+[1] # LogFile in current directory flog_name = 'log_'+os.path.split(self.path)[-1] print ' flog_name =',flog_name flog = open(flog_name,'w') flog.write('path:'+self.path+'\n') # MPSfile self.flmps = h5py.File(self.path+'/lmps','w') self.frmps = h5py.File(self.path+'/rmps','w') self.flmps['nsite'] = self.nsite self.frmps['nsite'] = self.nsite mpo_dmrg_io.saveQnum(self.flmps,0,self.qnuml[0]) mpo_dmrg_io.saveQnum(self.frmps,self.nsite,self.qnumr[-1]) # Initialize L-MPS by a single left sweep if fmps is None: # This is not allowed for using Qt. assert self.ifQt == False self.status = 'init' self.Dmax = self.schedule.MaxMs[0] self.crit_e = self.schedule.Tols[0] self.noise = self.schedule.Noises[0] mpo_dmrg_util.initMPS(self) # Use L-MPS from input else: self.comm.Barrier() # Not only requires qnuml for setting up mpo_dmrg_util self.qnuml = mpo_dmrg_io.loadQnums(fmps) # but also the sites are needed to be copied to flmps! mpo_dmrg_io.copyMPS(self.flmps,fmps,self.ifQt) self.comm.Barrier() # Initialize operators mpo_dmrg_util.initOps(self,fmps) # Optimize self.comm.Barrier() self.esweeps = [] self.psi0 = None self.eav = [] self.dwt = [] sitelst = range(self.nsite) ifconv = False deltaE = 1.e3 eold = 1.e3 isweep = -1 # Optimize following the schedule for isweep in range(self.schedule.maxiter): if rank == 0: print '\n'+'#'*30+' isweep = ',isweep,'#'*30 t0 = time.time() # Record status self.isweep = isweep # Setup parameters self.schedule.getParameters(self,isweep) # Optimization result1 = mpo_dmrg_opt.sweep(self,sitelst,self.ncsite,'R',ifsym=self.ifsym) result2 = mpo_dmrg_opt.sweep(self,sitelst,self.ncsite,'L',ifsym=self.ifsym) nmvp1,indx1,eav1,dwt1,elst1,dlst1 = result1 nmvp2,indx2,eav2,dwt2,elst2,dlst2 = result2 if rank == 0: mpo_dmrg_prt.flogWrite(self,flog,isweep,result1,result2) self.nmvp.append(nmvp1+nmvp2) self.esweeps += elst1+elst2 if eav1 < eav2: self.eav.append(eav1) self.dwt.append(dwt1) eav = eav1 else: self.eav.append(eav2) self.dwt.append(dwt2) eav = eav2 # Check convergence t1 = time.time() self.Energy = eav deltaE = eav-eold if rank == 0: print 'Summary: isweep=',isweep,' Emin=',eav,\ ' dE=%9.2e tol=%8.1e t=%8.1e s'%(deltaE,self.crit_tol,t1-t0) # Check convergence ifconv = self.schedule.checkConv(self,isweep,deltaE) eold = eav if ifconv: break # Save self.ifconv = ifconv self.nsweep = isweep + 1 self.deltaE = deltaE tf = time.time() self.comm.Barrier() # Adjust a little bit to allow isweep = 0. # The only problem is the R-MPS is not initialized. if rank == 0 and isweep != -1: mpo_dmrg_prt.finalSweep(self,tf-ti) if rank == 0: flog.close() self.comm.Barrier() return 0