def __init__(self, basis, xc=None, method="scf", mem=2000, root=None, nstates=None, auxbasis=None, keep_chk=True, **kwargs): super().__init__(**kwargs) self.basis = basis self.xc = xc self.method = method.lower() if self.xc and self.method != "tddft": self.method = "dft" # self.multistep = self.method in ("mp2 tddft".split()) self.mem = mem self.root = root self.nstates = nstates if self.method == "tddft": assert self.nstates, "nstates must be set with method='tddft'!" if self.track: assert self.root <= self.nstates, "'root' must be smaller " \ "than 'nstates'!" self.auxbasis = auxbasis self.keep_chk = keep_chk self.chkfile = None self.out_fn = "pyscf.out" self.unrestricted = self.mult > 1 lib.num_threads(self.pal)
def test_race_condition_skip(self): current_nthreads = lib.num_threads() lib.num_threads(32) mycc = cc.ccsd.CCSD(mf) mycc.max_memory = 1 mycc.conv_tol = 1e-10 ecc = mycc.kernel()[0] self.assertAlmostEqual(ecc, -0.2133432312951, 8) lib.num_threads(current_nthreads)
def contract1(self, cmat): ''' Contract 1 AO index with a dense matrix using sparse arithmetic on dense memory storage Args: cmat : np.ndarray of shape (nao, nmo) Returns: vPuv : np.ndarray of shape (nao, nmo, naux) stored in row-major order ''' if self.ndim == 3: return self.pack_mo() if not self.flags['C_CONTIGUOUS']: self = self.naux_slow() cmat = np.ascontiguousarray(cmat) nao = self.nmo[0] nmo = cmat.shape[1] if self.nent_max is None: self.get_sparsity_() vPuv = np.zeros((nao, nmo, self.naux), dtype=self.dtype).view(sparsedf_array) wrk = np.zeros((lib.num_threads(), self.nent_max, (self.naux + nmo)), dtype=self.dtype).view(sparsedf_array) libsint.SINT_SDCDERI_DDMAT( self.ctypes.data_as(ctypes.c_void_p), cmat.ctypes.data_as(ctypes.c_void_p), vPuv.ctypes.data_as(ctypes.c_void_p), wrk.ctypes.data_as(ctypes.c_void_p), self.iao_sort.ctypes.data_as(ctypes.c_void_p), self.iao_nent.ctypes.data_as(ctypes.c_void_p), self.iao_entlist.ctypes.data_as(ctypes.c_void_p), ctypes.c_int(nao), ctypes.c_int(self.naux), ctypes.c_int(nmo), ctypes.c_int(self.nent_max)) wrk = None return vPuv
def __init__(self, datafile): self.verbose = logger.NOTE self.stdout = sys.stdout self.max_memory = lib.param.MAX_MEMORY self.chkfile = datafile self.surfile = datafile + '.h5' self.scratch = lib.param.TMPDIR self.nthreads = lib.num_threads() self.inucs = [0, 0] self.occdrop = 1e-6 self.coef_C = 0.0093 self.coef_B = 5.9 ################################################## # don't modify the following attributes, they are not input options self.mol = None self.mo_coeff = None self.mo_occ = None self.natm = None self.coords = None self.charges = None self.nelectron = None self.charge = None self.spin = None self.npoints = None self.w1 = None self.p1 = None self.w2 = None self.p2 = None self._keys = set(self.__dict__.keys())
def contract2(self, vPuv): ''' Contract the auxbasis and one AO basis indices with multiplicand vPuv, as when computing the exchange matrix of Hartree--Fock. Args: vPuv : np.ndarray of shape (nao, nao, naux) stored in row-major order. The FIRST index is contracted with self ; the output of contract1 must be TRANSPOSED ON THE FIRST 2 INDICES in order to generate the vk matrix Returns: vk : np.ndarray of shape (nao, nao) ''' if self.ndim == 3: return self.pack_mo() if not self.flags['F_CONTIGUOUS']: self = self.naux_fast() if self.nent_max is None: self.get_sparsity_() nao = self.nmo[0] vk = np.zeros((nao, nao), dtype=self.dtype) wrk = np.zeros((lib.num_threads(), self.nent_max, self.naux), dtype=self.dtype) libsint.SINT_SDCDERI_VK( self.ctypes.data_as(ctypes.c_void_p), vPuv.ctypes.data_as(ctypes.c_void_p), vk.ctypes.data_as(ctypes.c_void_p), wrk.ctypes.data_as(ctypes.c_void_p), self.iao_sort.ctypes.data_as(ctypes.c_void_p), self.iao_nent.ctypes.data_as(ctypes.c_void_p), self.iao_entlist.ctypes.data_as(ctypes.c_void_p), ctypes.c_int(nao), ctypes.c_int(self.naux), ctypes.c_int(self.nent_max)) wrk = None vk = lib.hermi_sum(vk, inplace=True) vk[np.diag_indices(nao)] /= 2 return vk
def __init__(self, datafile): self.verbose = logger.NOTE self.stdout = sys.stdout self.max_memory = lib.param.MAX_MEMORY self.chkfile = datafile self.scratch = lib.param.TMPDIR self.nthreads = lib.num_threads() self.non0tab = False self.corr = False self.occdrop = 1e-6 self.chf = 0.0 self.small_rho_cutoff = 1e-6 self.prune = False ################################################## # don't modify the following attributes, they are not input options self.mol = lib.chkfile.load_mol(self.chkfile) self.grids = dft.Grids(self.mol) self.frevol = None self.rdm1 = None self.nocc = None self.mo_coeff = None self.mo_occ = None self.natm = None self.coords = None self.charges = None self.nelectron = None self.charge = None self.spin = None self.nprims = None self.nmo = None self._keys = set(self.__dict__.keys())
def __init__(self, datafile): self.verbose = lib.logger.NOTE self.stdout = sys.stdout self.max_memory = lib.param.MAX_MEMORY self.chkfile = datafile self.surfile = datafile + '.h5' self.scratch = lib.param.TMPDIR self.nthreads = lib.num_threads() ################################################## # don't modify the following attributes, they are not input options self.cell = None self.vol = None self.a = None self.b = None self.kpts = None self.nkpts = None self.ls = None self.natm = None self.coords = None self.charges = None self.nelectron = None self.charge = None self.spin = None self.frac = None self._keys = set(self.__dict__.keys())
def __init__(self, mycc): self._cc = mycc self.daemon = None nocc, nvir = mycc.t1.shape nmo = nocc + nvir nvir_seg = (nvir + mpi.pool.size - 1) // mpi.pool.size max_memory = mycc.max_memory - lib.current_memory()[0] max_memory = max(0, max_memory - nocc**3*13*lib.num_threads()*8/1e6) blksize = max(BLKMIN, (max_memory*.5e6/8/(6*nmo*nocc))**.5 - nocc/4) blksize = int(min(comm.allgather(min(nvir/6+2, nvir_seg/2+1, blksize)))) logger.debug1(mycc, 'GlobalDataHandler blksize %s', blksize) self.vranges = [] self.data_partition = [] self.segment_location = {} for task in range(mpi.pool.size): p0 = nvir_seg * task p1 = min(nvir, p0 + nvir_seg) self.vranges.append((p0, p1)) for j0, j1 in lib.prange(p0, p1, blksize): self.data_partition.append((j0, j1)) self.segment_location[j0] = task logger.debug1(mycc, 'data_partition %s', self.data_partition) logger.debug1(mycc, 'segment_location %s', self.segment_location)
def pyscf_dft(params, geometries, xc_functional): """ Function to run DFT along IRC using pySCF, returns array of energies at each geometry. """ if (os.path.isdir('pyscf_output')): pass else: os.makedirs("pyscf_output") print_header(params.outfile) energies = [] frontier_orb_energies = [] count = 0 start = time.time() lib.num_threads(params.nthreads) for geometry in geometries: output = open(params.outfile, "a") mol = gto.Mole() mol.output = 'pyscf_output/irc_%d.dat' % count mol.verbose = 0 mol.atom = geometry mol.basis = params.basis mol.charge = params.molecular_charge mol.spin = params.molecular_multiplicity - 1 mol.build() dft_obj = dft.RKS(mol) dft_obj.xc = xc_functional if (params.do_solvent): solv_obj = set_solvent_parameters(params, dft_obj) df = solv_obj.density_fit() else: df = dft_obj.density_fit() energy = df.scf() mo_e = df.mo_energy nocc = np.count_nonzero(df.mo_occ) homo_energy = mo_e[nocc - 1] lumo_energy = mo_e[nocc] homo_lumo = (homo_energy, lumo_energy) frontier_orb_energies.append(homo_lumo) energies.append(energy) output.write('{:>20.2f} {:>20.4f} {:>20.4f} {:>20.4f}\n'.format( params.coordinates[count], energy, homo_energy, lumo_energy)) count = count + 1 output.close() print_footer(params.outfile) end = time.time() print("pySCF Time = %f" % (end - start)) return energies, frontier_orb_energies
def __init__(self, datafile): self.verbose = logger.NOTE self.stdout = sys.stdout self.max_memory = lib.param.MAX_MEMORY self.chkfile = datafile self.surfile = datafile + '.h5' self.scratch = lib.param.TMPDIR self.nthreads = lib.num_threads() self.inuc = 0 self.epsiscp = 0.180 self.ntrial = 11 self.leb = True self.npang = 5810 self.nptheta = 90 self.npphi = 180 self.iqudt = 'legendre' self.rmaxsurf = 10.0 self.rprimer = 0.4 self.backend = 'rkck' self.epsroot = 1e-5 self.epsilon = 1e-5 self.step = 0.1 self.mstep = 120 self.corr = False self.occdrop = 1e-6 ################################################## # don't modify the following attributes, they are not input options self.mol = None self.mo_coeff = None self.mo_occ = None self.nocc = None self.natm = None self.coords = None self.charges = None self.xnuc = None self.xyzrho = None self.rpru = None self.grids = None self.rsurf = None self.nlimsurf = None self.rmin = None self.rmax = None self.nelectron = None self.charge = None self.spin = None self.atm = None self.bas = None self.nbas = None self.nprims = None self.nmo = None self.env = None self.ao_loc = None self.shls_slice = None self.nao = None self.non0tab = None self.cart = None self.rdm1 = None self.rcut = None self._keys = set(self.__dict__.keys())
def __init__(self, datafile): self.verbose = logger.NOTE self.stdout = sys.stdout self.max_memory = lib.param.MAX_MEMORY self.chkfile = datafile self.surfile = datafile+'.h5' self.scratch = lib.param.TMPDIR self.nthreads = lib.num_threads() self.inuc = 0 self.nrad = 101 self.iqudr = 'legendre' self.mapr = 'becke' self.betafac = 0.4 self.bnrad = 101 self.bnpang = 3074 self.biqudr = 'legendre' self.bmapr = 'becke' self.non0tab = False self.corr = False self.cas = False self.occdrop = 1e-6 self.nkpts = 1 ################################################## # don't modify the following attributes, they are not input options self.rdm1 = None self.nocc = None self.cell = None self.a = None self.b = None self.vol = None self.cell = None self.kpts = None self.ls = None self.mo_coeff = None self.mo_occ = None self.ntrial = None self.npang = None self.natm = None self.coords = None self.charges = None self.xnuc = None self.xyzrho = None self.agrids = None self.rsurf = None self.nlimsurf = None self.rmin = None self.rmax = None self.nelectron = None self.charge = None self.spin = None self.nprims = None self.nmo = None self.rad = None self.brad = None self._keys = set(self.__dict__.keys())
def oep_hess_old(jCa, orb_Ea, size, NOrb, NOcc): mo_coeff = np.reshape(jCa, (NOrb * NOrb), 'F') hess = np.ndarray((size, size), dtype=float, order='F') nthread = lib.num_threads() t0 = (time.clock(), time.time()) libhess.calc_hess_dm_fast(hess.ctypes.data_as(ctypes.c_void_p), \ mo_coeff.ctypes.data_as(ctypes.c_void_p), orb_Ea.ctypes.data_as(ctypes.c_void_p), \ ctypes.c_int(size), ctypes.c_int(NOrb), ctypes.c_int(NOcc), ctypes.c_int(nthread)) t1 = tools.timer("hessian construction", t0) return hess
def vk_svd(self, mo_coeff, mo_occ, thresh=1e-8): t0, w0 = time.process_time(), time.time() if self.ndim == 3: return self.pack_mo() if not self.flags['C_CONTIGUOUS']: self = self.naux_slow() nao = self.nmo[0] idx = np.abs(mo_occ) > 1e-8 nmo = np.count_nonzero(idx) global_K = min(self.nent_max, nmo) mo = mo_coeff[:, idx] * np.sqrt(mo_occ[idx])[None, :] cderi_lvec = np.zeros((nao, self.naux, global_K), dtype=self.dtype) mo_lvec = np.zeros((nao, self.nent_max, nmo), dtype=self.dtype) imo_nent = np.zeros_like(self.iao_nent) lwrk = (4 * global_K * global_K) + ( 8 * global_K) + self.nent_max * (global_K + self.naux + nmo) lwrk = max(lwrk, self.nent_max * (self.nent_max + nmo)) lwrk *= lib.num_threads() wrk = np.zeros(lwrk, dtype=self.dtype) libsint.SINT_SDCDERI_MO_LVEC( self.ctypes.data_as(ctypes.c_void_p), mo.ctypes.data_as(ctypes.c_void_p), cderi_lvec.ctypes.data_as(ctypes.c_void_p), mo_lvec.ctypes.data_as(ctypes.c_void_p), wrk.ctypes.data_as(ctypes.c_void_p), ctypes.c_double(thresh), self.iao_sort.ctypes.data_as(ctypes.c_void_p), self.iao_nent.ctypes.data_as(ctypes.c_void_p), self.iao_entlist.ctypes.data_as(ctypes.c_void_p), imo_nent.ctypes.data_as(ctypes.c_void_p), ctypes.c_int(nao), ctypes.c_int(self.naux), ctypes.c_int(nmo), ctypes.c_int(self.nent_max)) print("First C function time: {} clock ; {} wall".format( time.process_time() - t0, time.time() - w0)) t0, w0 = time.process_time(), time.time() wrk[:self.nent_max * (self.nent_max + nmo)] = 0.0 vk = np.zeros((nao, nao), dtype=mo_coeff.dtype) libsint.SINT_SDCDERI_DDMAT_MOSVD( cderi_lvec.ctypes.data_as(ctypes.c_void_p), mo_lvec.ctypes.data_as(ctypes.c_void_p), vk.ctypes.data_as(ctypes.c_void_p), wrk.ctypes.data_as(ctypes.c_void_p), imo_nent.ctypes.data_as(ctypes.c_void_p), ctypes.c_int(nao), ctypes.c_int(nmo), ctypes.c_int(self.naux), ctypes.c_int(self.nent_max), ctypes.c_int(global_K)) print("Second C function time: {} clock ; {} wall".format( time.process_time() - t0, time.time() - w0)) return vk
def mcfun_eval_xc_adapter(ni, xc_code): '''Wrapper to generate the eval_xc function required by mcfun''' try: import mcfun except ImportError: raise ImportError('This feature requires mcfun library.\n' 'Try install mcfun with `pip install mcfun`') xctype = ni._xc_type(xc_code) fn_eval_xc = functools.partial(__mcfun_fn_eval_xc, ni, xc_code, xctype) nproc = lib.num_threads() def eval_xc_eff(xc_code, rho, deriv=1, omega=None, xctype=None, verbose=None): return mcfun.eval_xc_eff( fn_eval_xc, rho, deriv, spin_samples=ni.spin_samples, collinear_threshold=ni.collinear_thrd, collinear_samples=ni.collinear_samples, workers=nproc) return eval_xc_eff
def oep_hess(jCa, orb_Ea, size, NOrb, NAlpha=None, mo_occ=None, smear=0.0, sym_tab=None): mo_coeff = np.reshape(jCa, (NOrb * NOrb), 'F') hess = np.ndarray((size, size), dtype=float, order='F') nthread = lib.num_threads() e_tol = 1e-4 occ_tol = 1e-8 #this should be small enough? t0 = tools.time0() if smear < 1e-8: if NAlpha is None: raise ValueError("NAlpha has to be set") libhess.calc_hess_dm_fast(hess.ctypes.data_as(ctypes.c_void_p), \ mo_coeff.ctypes.data_as(ctypes.c_void_p), orb_Ea.ctypes.data_as(ctypes.c_void_p), \ ctypes.c_int(size), ctypes.c_int(NOrb), ctypes.c_int(NAlpha), ctypes.c_int(nthread)) else: if mo_occ is None: raise ValueError("mo_occ has to be set") libhess.calc_hess_dm_fast_frac(hess.ctypes.data_as(ctypes.c_void_p), \ mo_coeff.ctypes.data_as(ctypes.c_void_p), orb_Ea.ctypes.data_as(ctypes.c_void_p), \ mo_occ.ctypes.data_as(ctypes.c_void_p),\ ctypes.c_int(size), ctypes.c_int(NOrb), ctypes.c_int(nthread),\ ctypes.c_double(smear), ctypes.c_double(e_tol), ctypes.c_double(occ_tol)) #tools.MatPrint(hess,"hess") t1 = tools.timer("hessian construction", t0) #if sym_tab is not None: # return symmtrize_hess(hess,sym_tab,size) return hess
def kernel(mycc, eris, t1=None, t2=None, verbose=logger.NOTE): cpu1 = cpu0 = (time.clock(), time.time()) log = logger.new_logger(mycc, verbose) if t1 is None: t1 = mycc.t1 if t2 is None: t2 = mycc.t2 nocc, nvir = t1.shape nmo = nocc + nvir dtype = numpy.result_type(t1, t2, eris.ovoo.dtype) if mycc.incore_complete: ftmp = None eris_vvop = numpy.zeros((nvir,nvir,nocc,nmo), dtype) else: ftmp = lib.H5TmpFile() eris_vvop = ftmp.create_dataset('vvop', (nvir,nvir,nocc,nmo), dtype) orbsym = _sort_eri(mycc, eris, nocc, nvir, eris_vvop, log) mo_energy, t1T, t2T, vooo, fvo, restore_t2_inplace = \ _sort_t2_vooo_(mycc, orbsym, t1, t2, eris) cpu1 = log.timer_debug1('CCSD(T) sort_eri', *cpu1) cpu2 = list(cpu1) orbsym = numpy.hstack((numpy.sort(orbsym[:nocc]),numpy.sort(orbsym[nocc:]))) o_ir_loc = numpy.append(0, numpy.cumsum(numpy.bincount(orbsym[:nocc], minlength=8))) v_ir_loc = numpy.append(0, numpy.cumsum(numpy.bincount(orbsym[nocc:], minlength=8))) o_sym = orbsym[:nocc] oo_sym = (o_sym[:,None] ^ o_sym).ravel() oo_ir_loc = numpy.append(0, numpy.cumsum(numpy.bincount(oo_sym, minlength=8))) nirrep = max(oo_sym) + 1 orbsym = orbsym.astype(numpy.int32) o_ir_loc = o_ir_loc.astype(numpy.int32) v_ir_loc = v_ir_loc.astype(numpy.int32) oo_ir_loc = oo_ir_loc.astype(numpy.int32) if dtype == numpy.complex: drv = _ccsd.libcc.CCsd_t_zcontract else: drv = _ccsd.libcc.CCsd_t_contract et_sum = numpy.zeros(1, dtype=dtype) def contract(a0, a1, b0, b1, cache): cache_row_a, cache_col_a, cache_row_b, cache_col_b = cache drv(et_sum.ctypes.data_as(ctypes.c_void_p), mo_energy.ctypes.data_as(ctypes.c_void_p), t1T.ctypes.data_as(ctypes.c_void_p), t2T.ctypes.data_as(ctypes.c_void_p), vooo.ctypes.data_as(ctypes.c_void_p), fvo.ctypes.data_as(ctypes.c_void_p), ctypes.c_int(nocc), ctypes.c_int(nvir), ctypes.c_int(a0), ctypes.c_int(a1), ctypes.c_int(b0), ctypes.c_int(b1), ctypes.c_int(nirrep), o_ir_loc.ctypes.data_as(ctypes.c_void_p), v_ir_loc.ctypes.data_as(ctypes.c_void_p), oo_ir_loc.ctypes.data_as(ctypes.c_void_p), orbsym.ctypes.data_as(ctypes.c_void_p), cache_row_a.ctypes.data_as(ctypes.c_void_p), cache_col_a.ctypes.data_as(ctypes.c_void_p), cache_row_b.ctypes.data_as(ctypes.c_void_p), cache_col_b.ctypes.data_as(ctypes.c_void_p)) cpu2[:] = log.timer_debug1('contract %d:%d,%d:%d'%(a0,a1,b0,b1), *cpu2) # The rest 20% memory for cache b mem_now = lib.current_memory()[0] max_memory = max(0, mycc.max_memory - mem_now) bufsize = (max_memory*.5e6/8-nocc**3*3*lib.num_threads())/(nocc*nmo) #*.5 for async_io bufsize *= .5 #*.5 upper triangular part is loaded bufsize *= .8 #*.8 for [a0:a1]/[b0:b1] partition bufsize = max(8, bufsize) log.debug('max_memory %d MB (%d MB in use)', max_memory, mem_now) with lib.call_in_background(contract, sync=not mycc.async_io) as async_contract: for a0, a1 in reversed(list(lib.prange_tril(0, nvir, bufsize))): cache_row_a = numpy.asarray(eris_vvop[a0:a1,:a1], order='C') if a0 == 0: cache_col_a = cache_row_a else: cache_col_a = numpy.asarray(eris_vvop[:a0,a0:a1], order='C') async_contract(a0, a1, a0, a1, (cache_row_a,cache_col_a, cache_row_a,cache_col_a)) for b0, b1 in lib.prange_tril(0, a0, bufsize/8): cache_row_b = numpy.asarray(eris_vvop[b0:b1,:b1], order='C') if b0 == 0: cache_col_b = cache_row_b else: cache_col_b = numpy.asarray(eris_vvop[:b0,b0:b1], order='C') async_contract(a0, a1, b0, b1, (cache_row_a,cache_col_a, cache_row_b,cache_col_b)) t2 = restore_t2_inplace(t2T) et_sum *= 2 if abs(et_sum[0].imag) > 1e-4: logger.warn(mycc, 'Non-zero imaginary part of CCSD(T) energy was found %s', et_sum[0]) et = et_sum[0].real log.timer('CCSD(T)', *cpu0) log.note('CCSD(T) correction = %.15g', et) return et
def comput_Amn(wf, Rc=None, lmr=None, zaxis=None, xaxis=None, zona=None, bands=None, nband=None, kpts=np.zeros((1, 3)), max_memory=None): if Rc is None: Rc = wf.Rc if lmr is None: lmr = wf.lmr if zaxis is None: zaxis = wf.zaxis if xaxis is None: xaxis = wf.xaxis if zona is None: zona = wf.zona if bands is None: bands = wf.bands if nband is None: nband = wf.nband if max_memory is None: max_memory = wf.max_memory nk = len(kpts) mf = wf.mf mo_coeff = mf.mo_coeff cell = wf.cell mydf = mf.with_df gs = mydf.gs coords = cell.gen_uniform_grids(gs) ngs = len(coords) ni = mydf._numint weight = cell.vol / ngs aoR = ni.eval_ao(cell, coords, kpts, non0tab=None) a = cell.lattice_vectors() R = np.dot(Rc, a) #g_r = comput_g_r(R,lmr,zaxis,xaxis,zona,nband,coords) #parallel block g_r = np.ndarray((nband * ngs)) from pyscf import lib max_mem = wf.max_memory - lib.current_memory()[0] print('available mem (Mb) = ', max_mem) blk_size = min(ngs, (max_mem * 1e6 / 8 - nband * ngs * 3) / 12 / 16) nblks = ngs // blk_size if (nblks <= 1): nblks = lib.num_threads() blk_size = ngs // nblks #g_r_blks = np.concatenate(tuple[g_r_split[i] for i in range(nblks)],axis=0) libmisc.comput_g_r(ctypes.c_int(blk_size), ctypes.c_int(nblks), \ g_r.ctypes.data_as(ctypes.c_void_p), coords.ctypes.data_as(ctypes.c_void_p),ctypes.c_int(ngs), ctypes.c_int(nband), \ R.ctypes.data_as(ctypes.c_void_p),lmr.ctypes.data_as(ctypes.c_void_p), zaxis.ctypes.data_as(ctypes.c_void_p), \ xaxis.ctypes.data_as(ctypes.c_void_p),zona.ctypes.data_as(ctypes.c_void_p)) g_r_split = np.split(g_r, [i * nband * blk_size for i in range(1, nblks)]) for i in range(nblks): g_r_split[i] = np.reshape(g_r_split[i], (nband, -1)) g_r = np.concatenate([g_r_split[i] for i in range(nblks)], axis=1) ''' pool = Pool() results = [pool.apply_async(comput_g_r_para, (i, R,lmr,zaxis,xaxis,zona,coords,)) for i in range(nband) ] pool.close() pool.join() for i in range(nband): g_r[i] = results[i].get() ''' ''' #assume 8 proc blk_size = ngs//8 tmp = np.split(coords,[blk_size,blk_size*2,blk_size*3,blk_size*4,blk_size*5,blk_size*6,blk_size*7]) for i in range(nband): pool = Pool(8,maxtasksperchild=1) results = [pool.apply_async(comput_g_r_para, (i, R,lmr,zaxis,xaxis,zona,coords_blk,)) for blk,coords_blk in enumerate(tmp) ] pool.close() pool.join() for blk in range(8): index1 = blk*blk_size index2 = index1+blk_size if(blk == 7): index2 = ngs g_r[i][index1:index2] = results[blk].get() del tmp #end parallel block ''' print('available mem (Mb) = ', wf.max_memory - lib.current_memory()[0]) nao = cell.nao_nr() Amun = np.zeros((nk, nao, nband), dtype=np.complex128) Amn = np.zeros((nk, nband, nband), dtype=np.complex128) for k, aoR_k in enumerate(aoR): Amun[k] = weight * lib.dot(aoR_k.T.conj(), g_r.T) for k in range(nk): Amn[k] = lib.dot(mo_coeff[:, bands].T.conj(), Amun[k]) return Amn
def kernel(mycc, eris, t1=None, t2=None, verbose=logger.NOTE): cpu1 = cpu0 = (logger.process_clock(), logger.perf_counter()) log = logger.new_logger(mycc, verbose) if t1 is None: t1 = mycc.t1 if t2 is None: t2 = mycc.t2 nocc, nvir = t1.shape nmo = nocc + nvir dtype = numpy.result_type(t1, t2, eris.ovoo.dtype) if mycc.incore_complete: ftmp = None eris_vvop = numpy.zeros((nvir, nvir, nocc, nmo), dtype) else: ftmp = lib.H5TmpFile() eris_vvop = ftmp.create_dataset('vvop', (nvir, nvir, nocc, nmo), dtype) orbsym = _sort_eri(mycc, eris, nocc, nvir, eris_vvop, log) mo_energy, t1T, t2T, vooo, fvo, restore_t2_inplace = \ _sort_t2_vooo_(mycc, orbsym, t1, t2, eris) cpu1 = log.timer_debug1('CCSD(T) sort_eri', *cpu1) cpu2 = list(cpu1) orbsym = numpy.hstack( (numpy.sort(orbsym[:nocc]), numpy.sort(orbsym[nocc:]))) o_ir_loc = numpy.append( 0, numpy.cumsum(numpy.bincount(orbsym[:nocc], minlength=8))) v_ir_loc = numpy.append( 0, numpy.cumsum(numpy.bincount(orbsym[nocc:], minlength=8))) o_sym = orbsym[:nocc] oo_sym = (o_sym[:, None] ^ o_sym).ravel() oo_ir_loc = numpy.append(0, numpy.cumsum(numpy.bincount(oo_sym, minlength=8))) nirrep = max(oo_sym) + 1 orbsym = orbsym.astype(numpy.int32) o_ir_loc = o_ir_loc.astype(numpy.int32) v_ir_loc = v_ir_loc.astype(numpy.int32) oo_ir_loc = oo_ir_loc.astype(numpy.int32) if dtype == numpy.complex: drv = _ccsd.libcc.CCsd_t_zcontract else: drv = _ccsd.libcc.CCsd_t_contract et_sum = numpy.zeros(1, dtype=dtype) def contract(a0, a1, b0, b1, cache): cache_row_a, cache_col_a, cache_row_b, cache_col_b = cache drv(et_sum.ctypes.data_as(ctypes.c_void_p), mo_energy.ctypes.data_as(ctypes.c_void_p), t1T.ctypes.data_as(ctypes.c_void_p), t2T.ctypes.data_as(ctypes.c_void_p), vooo.ctypes.data_as(ctypes.c_void_p), fvo.ctypes.data_as(ctypes.c_void_p), ctypes.c_int(nocc), ctypes.c_int(nvir), ctypes.c_int(a0), ctypes.c_int(a1), ctypes.c_int(b0), ctypes.c_int(b1), ctypes.c_int(nirrep), o_ir_loc.ctypes.data_as(ctypes.c_void_p), v_ir_loc.ctypes.data_as(ctypes.c_void_p), oo_ir_loc.ctypes.data_as(ctypes.c_void_p), orbsym.ctypes.data_as(ctypes.c_void_p), cache_row_a.ctypes.data_as(ctypes.c_void_p), cache_col_a.ctypes.data_as(ctypes.c_void_p), cache_row_b.ctypes.data_as(ctypes.c_void_p), cache_col_b.ctypes.data_as(ctypes.c_void_p)) cpu2[:] = log.timer_debug1('contract %d:%d,%d:%d' % (a0, a1, b0, b1), *cpu2) # The rest 20% memory for cache b mem_now = lib.current_memory()[0] max_memory = max(0, mycc.max_memory - mem_now) bufsize = (max_memory * .5e6 / 8 - nocc**3 * 3 * lib.num_threads()) / ( nocc * nmo) #*.5 for async_io bufsize *= .5 #*.5 upper triangular part is loaded bufsize *= .8 #*.8 for [a0:a1]/[b0:b1] partition bufsize = max(8, bufsize) log.debug('max_memory %d MB (%d MB in use)', max_memory, mem_now) with lib.call_in_background(contract, sync=not mycc.async_io) as async_contract: for a0, a1 in reversed(list(lib.prange_tril(0, nvir, bufsize))): cache_row_a = numpy.asarray(eris_vvop[a0:a1, :a1], order='C') if a0 == 0: cache_col_a = cache_row_a else: cache_col_a = numpy.asarray(eris_vvop[:a0, a0:a1], order='C') async_contract( a0, a1, a0, a1, (cache_row_a, cache_col_a, cache_row_a, cache_col_a)) for b0, b1 in lib.prange_tril(0, a0, bufsize / 8): cache_row_b = numpy.asarray(eris_vvop[b0:b1, :b1], order='C') if b0 == 0: cache_col_b = cache_row_b else: cache_col_b = numpy.asarray(eris_vvop[:b0, b0:b1], order='C') async_contract( a0, a1, b0, b1, (cache_row_a, cache_col_a, cache_row_b, cache_col_b)) t2 = restore_t2_inplace(t2T) et_sum *= 2 if abs(et_sum[0].imag) > 1e-4: logger.warn(mycc, 'Non-zero imaginary part of CCSD(T) energy was found %s', et_sum[0]) et = et_sum[0].real log.timer('CCSD(T)', *cpu0) log.note('CCSD(T) correction = %.15g', et) return et
def setUp(self): super().setUp() lib.param.TMPDIR = None lib.num_threads(1)
There is no flag to control the program to do density fitting for 2-electron integration. The way to call density fitting is to decorate the existed scf object with scf.density_fit function. NOTE scf.density_fit function generates a new object, which works exactly the same way as the regular scf method. The density fitting scf object is an independent object to the regular scf object which is to be decorated. By doing so, density fitting can be applied anytime, anywhere in your script without affecting the exsited scf object. See also: examples/df/00-with_df.py examples/df/01-auxbasis.py ''' lib.num_threads(16) mol = gto.Mole() mol.build( verbose=7, atom=''' ''', unit='Angstrom', basis='ccpvtz', max_memory=40000, ) # # By default optimal auxiliary basis (if possible) or even-tempered gaussian # functions are used fitting basis. You can assign with_df.auxbasis to change # the change the fitting basis. #
#!/usr/bin/env python3 ## vi: tabstop=4 shiftwidth=4 softtabstop=4 expandtab import adcc import libadcc from pyscf import gto, scf, lib from matplotlib import pyplot as plt import json lib.num_threads(32) thread_pool = libadcc.ThreadPool(32, 32) # Run SCF in pyscf mol = gto.M( atom=""" C 0.27812370431808 1.67799706433198 0.05303450044432 C 0.45285037034284 1.90525730119212 -1.44800930678034 N 1.11651102957946 0.80438639287253 -2.13069466714461 C 0.25344686176467 -0.22440281232970 -2.69043511896325 C -0.15209273138513 0.03955743307279 -4.14038489580455 C 2.48472368371448 0.74440359776252 -2.25453347585288 C 3.32837158699297 1.69400459940962 -1.60757225981238 C 4.70363498248368 1.63215484310263 -1.73872425413962 C 5.32417908319115 0.63143577302088 -2.50381678215105 C 4.48965804951387 -0.30522723634995 -3.13102587447949 C 3.10544707901087 -0.26389337931057 -3.02600350310044 O 5.03761194046719 -1.30070694623165 -3.88564801979747 C 6.38696309523395 -1.38887650151956 -4.02212638927200 C 6.90650769076478 -2.39142877944742 -4.76367723162242 C 8.35585235683613 -2.54734162576218 -4.93914435256588 O 8.83416170782160 -3.46044106358362 -5.58937445211989
from pyscf import scf,dft, gto, lib from automr import guess, autocas lib.num_threads(8) #mf=guess.from_fch_simp("v2.fchk", xc='pbe0') #mf2.verbose=9 #mf2.stability() mol = gto.Mole(atom='''V 0.0 0.0 0.0; V 0.0 0.0 1.77''', basis='def2-tzvp', spin=2) mol.verbose = 4 mol.build() mf = scf.UHF(mol) mf.kernel() mf = guess.check_stab(mf, newton=True) mf2 = autocas.cas(mf, (8, (5,3)) ) mf4 = autocas.nevpt2(mf2) mol2 = gto.Mole(atom='''V 0.0 0.0 0.0''', basis='def2-tzvp', spin=3) mol2.verbose = 4 mol2.build() mfb = scf.UHF(mol2) mfb.kernel() mfb = guess.check_stab(mfb, newton=True) mfb2 = autocas.cas(mfb) mfb4 = autocas.nevpt2(mfb2) mol3 = gto.Mole(atom='''V 0.0 0.0 0.0''', basis='def2-tzvp', spin=1) mol3.verbose = 4 mol3.build() mfc = scf.UHF(mol3) mfc.kernel()
def grad_calc(params, current_geom, mol): """ Uses Psi4/pySCF to calculate the energy gradient and returns the gradient and energy. Here any of the keywords the user provides in the .json input are used to set the options for the energy calculation. Parameters: ---------- params(self) -- contains initialized shared parameters. current_geom(np array) -- Matrix of size natoms x 3 containing the geometry. mol(psi4.Molecule) -- Psi4 molecule object containing the current molecule. Returns: ------- grad_mw(np array) -- Mass weighted gradient matrix of size natoms x 3. E(float) -- single-point energy from Psi4 calculation. """ if (params.qm_program == 'pyscf'): pymol = gto.Mole() pymol.verbose = 0 geom_vec = [] for i in range(params.natoms): atom = [ params.symbols[i], ] atom_coords = [] for j in range(3): atom_coords.append(current_geom[i][j]) atom_coords = tuple(atom_coords) atom.append(atom_coords) geom_vec.append(atom) #print(geom_vec) pymol.atom = geom_vec pymol.unit = 'Bohr' pymol.basis = params.basis pymol.charge = params.molecular_charge pymol.spin = params.molecular_multiplicity - 1 pymol.build() #TODO: PySCF 1.6.2 changes the way solvent is called for gradients, change this here # they also added support for ddPCM, YAY! Let's add it in! if (params.method == "scf"): scf_obj = scf.RHF(pymol) if (params.method == "dft"): scf_obj = dft.RKS(pymol) scf_obj.xc = params.xc_functional if (params.do_solvent): solv_obj = scf_obj.DDCOSMO() solv_obj.with_solvent.eps = params.eps lib.num_threads(params.nthreads) E = solv_obj.scf() grad = solv_obj.nuc_grad_method().kernel() else: lib.num_threads(params.nthreads) E = scf_obj.scf() grad = scf_obj.nuc_grad_method().kernel() if (params.qm_program == 'psi4'): mol.set_geometry(psi4.core.Matrix.from_array(current_geom)) mol.fix_orientation(True) mol.fix_com(True) mol.reset_point_group('c1') grad_method = "%s/%s" % (params.method, params.basis) psi4.core.set_output_file("psi4_out.dat", False) psi4.set_options(params.keywords) psi4.set_num_threads(params.nthreads) E, wfn = psi4.energy(grad_method, return_wfn=True) psi4.set_num_threads(params.nthreads) grad = np.asarray(psi4.gradient(grad_method, ref_wfn=wfn)) #print(grad) return grad
expRGy, 1. / mesh[1], c=buf.reshape(-1, mesh[1])) f = lib.dot(f.reshape(mesh[2], -1).T, expRGz, 1. / mesh[2], c=out[i].reshape(-1, mesh[2])) return out.reshape(-1, *mesh) if FFT_ENGINE == 'FFTW': # pyfftw is slower than np.fft in most cases try: import pyfftw pyfftw.interfaces.cache.enable() nproc = lib.num_threads() def _fftn_wrapper(a): return pyfftw.interfaces.numpy_fft.fftn(a, axes=(1, 2, 3), threads=nproc) def _ifftn_wrapper(a): return pyfftw.interfaces.numpy_fft.ifftn(a, axes=(1, 2, 3), threads=nproc) except ImportError: def _fftn_wrapper(a): return np.fft.fftn(a, axes=(1, 2, 3))
import numpy as np from pyscf import gto, scf, lib lib.num_threads(1) geometry = ''' O 0.0000000000 0.0000000000 0.1084050200 H -0.7539036400 0.0000000000 -0.4794322700 H 0.7539036400 0.0000000000 -0.4794322700 ''' mol = gto.Mole() mol.atom = geometry mol.basis = '3-21g' mol.build() mf = scf.RHF(mol) mf.scf() Fao = mf.get_fock() Fmo = mf.mo_coeff.T @ Fao @ mf.mo_coeff np.set_printoptions(formatter={'float': lambda Fmo: "{0:0.6f}".format(Fmo)}) print('F_mo') print(Fmo) print()
e, ci = fci.direct_spin0.kernel(h1, h2, 10, 10, ecore=mol.energy_nuc(), ci0=ci, max_cycle=500, max_space=100, verbose=5) print(e) e, ci = fci.direct_spin0.kernel(h1, h2, 10, 10, ecore=mol.energy_nuc(), ci0=ci, max_cycle=500, max_space=100, verbose=5) print(e) # # Reducing OMP threads can improve the numerical stability # # Set OMP_NUM_THREADS to 1 lib.num_threads(1) e, ci = fci.direct_spin0.kernel(h1, h2, 10, 10, ecore=mol.energy_nuc(), max_cycle=500, max_space=100, verbose=5) print(e) e, ci = fci.direct_spin0.kernel(h1, h2, 10, 10, ecore=mol.energy_nuc(), ci0=ci, max_cycle=500, max_space=100, verbose=5) print(e) # # Another Example. # import h5py with h5py.File('spin_op_hamiltonian.h5', 'r') as f: h1 = lib.unpack_tril(f['h1'].value)
expRGz = np.exp(np.einsum('x,k->xk', 2j*np.pi*np.arange(mesh[2]), Gz)) out = np.empty(g.shape, dtype=np.complex128) buf = np.empty(mesh, dtype=np.complex128) for i, gi in enumerate(g): buf[:] = gi.reshape(mesh) f = lib.dot(buf.reshape(mesh[0],-1).T, expRGx, 1./mesh[0], c=out[i].reshape(-1,mesh[0])) f = lib.dot(f.reshape(mesh[1],-1).T, expRGy, 1./mesh[1], c=buf.reshape(-1,mesh[1])) f = lib.dot(f.reshape(mesh[2],-1).T, expRGz, 1./mesh[2], c=out[i].reshape(-1,mesh[2])) return out.reshape(-1, *mesh) if FFT_ENGINE == 'FFTW': # pyfftw is slower than np.fft in most cases try: import pyfftw pyfftw.interfaces.cache.enable() nproc = lib.num_threads() def _fftn_wrapper(a): return pyfftw.interfaces.numpy_fft.fftn(a, axes=(1,2,3), threads=nproc) def _ifftn_wrapper(a): return pyfftw.interfaces.numpy_fft.ifftn(a, axes=(1,2,3), threads=nproc) except ImportError: def _fftn_wrapper(a): return np.fft.fftn(a, axes=(1,2,3)) def _ifftn_wrapper(a): return np.fft.ifftn(a, axes=(1,2,3)) elif FFT_ENGINE == 'NUMPY': def _fftn_wrapper(a): return np.fft.fftn(a, axes=(1,2,3)) def _ifftn_wrapper(a): return np.fft.ifftn(a, axes=(1,2,3))
# # Generate the DMRG-CASSCF initial guess with AVAS (atomic valence active space) method. # norb_act, ne_act, mos = avas.avas(mf, ['V 3s', 'V 3p', 'V 3d', 'O 2p', 'Cl 3p']) # # Pass 1 # DMRG-CASSCF calculation with small M. In many systems, the mcscf orbitals has # weak dependence to the quality of the active space solution. We can use small # M to approximate the active space wave function and increase M for DMRG-CASCI # and DMRG-NEVPT2 in next step. # mc = dmrgscf.DMRGSCF(mf, norb_act, ne_act) mc.fcisolver.maxM = 500 mc.fcisolver.extraline = ['num_thrds %d'%lib.num_threads(), 'warmup local_2site'] mc.fcisolver.memory = 100 # GB mc.conv_tol = 1e-6 mc.state_average_([.2]*3) mc.kernel(mos) mc_orbs = mc.mo_coeff # # Pass 2 # A separated DMRG-CASCI calculation based on DMRG-CASSCF orbitals obtained and # DMRG solver with large bond dimension to improve the multi configurational # wave function. # mc = mcscf.CASCI(mf, norb_act, ne_act) mc.fcisolver = dmrgscf.DMRGCI(mol)
def __init__(self, num_threads=1): """ In the init, the pyscf Mole object and scf.ks object will be created Input: molecule:string the string for the molecule where all the element symbol are present i.e.: CHHHH and not Ch4 positions:list of list The positions for each atoms in angstromg spin:int total spin of the molecule approx:string the functional in pyscf format basis:string the basis set in pyscf format num_threads:int the number of threads for pyscf """ lib.num_threads(num_threads) # this is an object by itself so we initialize it with None self.mf = None # Coordinates, weights, number of grid points and atomic orbital values (hopefully calculated by pyscf at every grid point) self.coords = 0.0 self.weights = 0.0 self.ngrid = 0 self.aovalues = 0.0 # density matrices self.dm = 0.0 self.dm_up = 0.0 self.dm_down = 0.0 # densities self.rho_up = 0.0 self.rho_down = 0.0 self.rho_tot = 0.0 # density derivarive's components self.dx_rho_up = 0.0 self.dy_rho_up = 0.0 self.dz_rho_up = 0.0 self.dx_rho_down = 0.0 self.dy_rho_down = 0.0 self.dz_rho_down = 0.0 # gradient of the density self.gradrho_up = 0.0 self.gradrho_down = 0.0 # laplacian of the density self.laprho_up = 0.0 self.laprho_down = 0.0 # kinetic energy density self.tau_up = 0.0 self.tau_down = 0.0 # additional parameters self.D_up = 0.0 self.D_down = 0.0 # curvature of the exact exchange hole self.Q_up = 0.0 self.Q_down = 0.0 eps_x_exact_up = 0.0 eps_x_exact_down = 0.0
def build_se_part(agf2, eri, gf_occ, gf_vir, os_factor=1.0, ss_factor=1.0): ''' Builds either the auxiliaries of the occupied self-energy, or virtual if :attr:`gf_occ` and :attr:`gf_vir` are swapped. Args: eri : _ChemistsERIs Electronic repulsion integrals gf_occ : GreensFunction Occupied Green's function gf_vir : GreensFunction Virtual Green's function Kwargs: os_factor : float Opposite-spin factor for spin-component-scaled (SCS) calculations. Default 1.0 ss_factor : float Same-spin factor for spin-component-scaled (SCS) calculations. Default 1.0 Returns: :class:`SelfEnergy` ''' cput0 = (logger.process_clock(), logger.perf_counter()) log = logger.Logger(agf2.stdout, agf2.verbose) assert type(gf_occ) is aux.GreensFunction assert type(gf_vir) is aux.GreensFunction nmo = eri.nmo nocc, nvir = gf_occ.naux, gf_vir.naux naux = agf2.with_df.get_naoaux() tol = agf2.weight_tol facs = dict(os_factor=os_factor, ss_factor=ss_factor) ei, ci = gf_occ.energy, gf_occ.coupling ea, ca = gf_vir.energy, gf_vir.coupling qxi, qja = _make_qmo_eris_incore(agf2, eri, (ci, ci, ca)) himem_required = naux * (nvir + nmo) + (nocc * nvir) * (2 * nmo + 1) + ( 2 * nmo**2) himem_required *= 8e-6 himem_required *= lib.num_threads() if ((himem_required * 1.05 + lib.current_memory()[0]) > agf2.max_memory and agf2.allow_lowmem_build) or agf2.allow_lowmem_build == 'force': log.debug( 'Thread-private memory overhead %.3f exceeds max_memory, using ' 'low-memory version.', himem_required) vv, vev = _agf2.build_mats_dfragf2_lowmem(qxi, qja, ei, ea, **facs) else: vv, vev = _agf2.build_mats_dfragf2_incore(qxi, qja, ei, ea, **facs) e, c = _agf2.cholesky_build(vv, vev) se = aux.SelfEnergy(e, c, chempot=gf_occ.chempot) se.remove_uncoupled(tol=tol) if not (agf2.frozen is None or agf2.frozen == 0): mask = ragf2.get_frozen_mask(agf2) coupling = np.zeros((nmo, se.naux)) coupling[mask] = se.coupling se = aux.SelfEnergy(se.energy, coupling, chempot=se.chempot) log.timer('se part', *cput0) return se
def overlap(cibra, ciket, nmo, nocc, s=None): '''Overlap between two CISD wavefunctions. Args: s : 2D array The overlap matrix of non-orthogonal one-particle basis ''' if s is None: return dot(cibra, ciket, nmo, nocc) DEBUG = True nvir = nmo - nocc nov = nocc * nvir bra0, bra1, bra2 = cisdvec_to_amplitudes(cibra, nmo, nocc) ket0, ket1, ket2 = cisdvec_to_amplitudes(ciket, nmo, nocc) # Sort the ket orbitals to make the orbitals in bra one-one mapt to orbitals # in ket. if ((not DEBUG) and abs(numpy.linalg.det(s[:nocc, :nocc]) - 1) < 1e-2 and abs(numpy.linalg.det(s[nocc:, nocc:]) - 1) < 1e-2): ket_orb_idx = numpy.where(abs(s) > 0.9)[1] s = s[:, ket_orb_idx] oidx = ket_orb_idx[:nocc] vidx = ket_orb_idx[nocc:] - nocc ket1 = ket1[oidx[:, None], vidx] ket2 = ket2[oidx[:, None, None, None], oidx[:, None, None], vidx[:, None], vidx] ooidx = numpy.tril_indices(nocc, -1) vvidx = numpy.tril_indices(nvir, -1) bra2aa = bra2 - bra2.transpose(1, 0, 2, 3) bra2aa = lib.take_2d(bra2aa.reshape(nocc**2, nvir**2), ooidx[0] * nocc + ooidx[1], vvidx[0] * nvir + vvidx[1]) ket2aa = ket2 - ket2.transpose(1, 0, 2, 3) ket2aa = lib.take_2d(ket2aa.reshape(nocc**2, nvir**2), ooidx[0] * nocc + ooidx[1], vvidx[0] * nvir + vvidx[1]) occlist0 = numpy.arange(nocc).reshape(1, nocc) occlists = numpy.repeat(occlist0, 1 + nov + bra2aa.size, axis=0) occlist0 = occlists[:1] occlist1 = occlists[1:1 + nov] occlist2 = occlists[1 + nov:] ia = 0 for i in range(nocc): for a in range(nocc, nmo): occlist1[ia, i] = a ia += 1 ia = 0 for i in range(nocc): for j in range(i): for a in range(nocc, nmo): for b in range(nocc, a): occlist2[ia, i] = a occlist2[ia, j] = b ia += 1 na = len(occlists) if DEBUG: trans = numpy.empty((na, na)) for i, idx in enumerate(occlists): s_sub = s[idx].T.copy() minors = s_sub[occlists] trans[i, :] = numpy.linalg.det(minors) # Mimic the transformation einsum('ab,ap->pb', FCI, trans). # The wavefunction FCI has the [excitation_alpha,excitation_beta] # representation. The zero blocks like FCI[S_alpha,D_beta], # FCI[D_alpha,D_beta], are explicitly excluded. bra_mat = numpy.zeros((na, na)) bra_mat[0, 0] = bra0 bra_mat[0, 1:1 + nov] = bra_mat[1:1 + nov, 0] = bra1.ravel() bra_mat[0, 1 + nov:] = bra_mat[1 + nov:, 0] = bra2aa.ravel() bra_mat[1:1 + nov, 1:1 + nov] = bra2.transpose(0, 2, 1, 3).reshape(nov, nov) ket_mat = numpy.zeros((na, na)) ket_mat[0, 0] = ket0 ket_mat[0, 1:1 + nov] = ket_mat[1:1 + nov, 0] = ket1.ravel() ket_mat[0, 1 + nov:] = ket_mat[1 + nov:, 0] = ket2aa.ravel() ket_mat[1:1 + nov, 1:1 + nov] = ket2.transpose(0, 2, 1, 3).reshape(nov, nov) ovlp = lib.einsum('ab,ap,bq,pq->', bra_mat, trans, trans, ket_mat) else: nov1 = 1 + nov noovv = bra2aa.size bra_SS = numpy.zeros((nov1, nov1)) bra_SS[0, 0] = bra0 bra_SS[0, 1:] = bra_SS[1:, 0] = bra1.ravel() bra_SS[1:, 1:] = bra2.transpose(0, 2, 1, 3).reshape(nov, nov) ket_SS = numpy.zeros((nov1, nov1)) ket_SS[0, 0] = ket0 ket_SS[0, 1:] = ket_SS[1:, 0] = ket1.ravel() ket_SS[1:, 1:] = ket2.transpose(0, 2, 1, 3).reshape(nov, nov) trans_SS = numpy.empty((nov1, nov1)) trans_SD = numpy.empty((nov1, noovv)) trans_DS = numpy.empty((noovv, nov1)) occlist01 = occlists[:nov1] for i, idx in enumerate(occlist01): s_sub = s[idx].T.copy() minors = s_sub[occlist01] trans_SS[i, :] = numpy.linalg.det(minors) minors = s_sub[occlist2] trans_SD[i, :] = numpy.linalg.det(minors) s_sub = s[:, idx].copy() minors = s_sub[occlist2] trans_DS[:, i] = numpy.linalg.det(minors) ovlp = lib.einsum('ab,ap,bq,pq->', bra_SS, trans_SS, trans_SS, ket_SS) ovlp += lib.einsum('ab,a ,bq, q->', bra_SS, trans_SS[:, 0], trans_SD, ket2aa.ravel()) ovlp += lib.einsum('ab,ap,b ,p ->', bra_SS, trans_SD, trans_SS[:, 0], ket2aa.ravel()) ovlp += lib.einsum(' b, p,bq,pq->', bra2aa.ravel(), trans_SS[0, :], trans_DS, ket_SS) ovlp += lib.einsum(' b, p,b ,p ->', bra2aa.ravel(), trans_SD[0, :], trans_DS[:, 0], ket2aa.ravel()) ovlp += lib.einsum('a ,ap, q,pq->', bra2aa.ravel(), trans_DS, trans_SS[0, :], ket_SS) ovlp += lib.einsum('a ,a , q, q->', bra2aa.ravel(), trans_DS[:, 0], trans_SD[0, :], ket2aa.ravel()) # FIXME: whether to approximate the overlap between double excitation coefficients if numpy.linalg.norm(bra2aa) * numpy.linalg.norm(ket2aa) < 1e-4: # Skip the overlap if coefficients of double excitation are small enough pass if (abs(numpy.linalg.det(s[:nocc, :nocc]) - 1) < 1e-2 and abs(numpy.linalg.det(s[nocc:, nocc:]) - 1) < 1e-2): # If the overlap matrix close to identity enough, use the <D|D'> overlap # for orthogonal single-particle basis to approximate the overlap # for non-orthogonal basis. ovlp += numpy.dot(bra2aa.ravel(), ket2aa.ravel()) * trans_SS[0, 0] * 2 else: from multiprocessing import sharedctypes, Process buf_ctypes = sharedctypes.RawArray('d', noovv) trans_ket = numpy.ndarray(noovv, buffer=buf_ctypes) def trans_dot_ket(i0, i1): for i in range(i0, i1): s_sub = s[occlist2[i]].T.copy() minors = s_sub[occlist2] trans_ket[i] = numpy.linalg.det(minors).dot(ket2aa.ravel()) nproc = lib.num_threads() if nproc > 1: seg = (noovv + nproc - 1) // nproc ps = [] for i0, i1 in lib.prange(0, noovv, seg): p = Process(target=trans_dot_ket, args=(i0, i1)) ps.append(p) p.start() [p.join() for p in ps] else: trans_dot_ket(0, noovv) ovlp += numpy.dot(bra2aa.ravel(), trans_ket) * trans_SS[0, 0] * 2 return ovlp
for k in range(nmo): mo = mo_cart[:, k] fout.write( 'MO %-12d OCC NO = %12.8f ORB. ENERGY = %12.8f\\n' % (k + 1, mo_occ[k], mo_energy[k])) for i0, i1 in lib.prange(0, nprim, 5): fout.write(' %s\\n' % ' '.join('%15.8E' % x for x in mo[i0:i1])) fout.write('END DATA\\n') fout.write(' THE SCF ENERGY =%20.12f THE VIRIAL(-V/T)= 0.00000000\\n' % tot_ener) from pyscf.pbc import gto, scf, dft, df from pyscf import lib lib.num_threads(6) cell = gto.M( atom='''Ca 2.7254760000 2.7254760000 2.7254760000 Ca 2.7254760000 0.0000000000 0.0000000000 Ca 0.0000000000 2.7254760000 0.0000000000 F 4.0882140000 4.0882140000 4.0882140000 F 1.3627380000 4.0882140000 1.3627380000 F 4.0882140000 1.3627380000 1.3627380000 F 1.3627380000 1.3627380000 4.0882140000 F 4.0882140000 4.0882140000 1.3627380000 F 4.0882140000 1.3627380000 4.0882140000 F 1.3627380000 4.0882140000 4.0882140000 Ca 0.0000000000 0.0000000000 2.7254760000 F 1.3627380000 1.3627380000 1.3627380000 ''', verbose=5,
There is no flag to control the program to do density fitting for 2-electron integration. The way to call density fitting is to decorate the existed scf object with scf.density_fit function. NOTE scf.density_fit function generates a new object, which works exactly the same way as the regular scf method. The density fitting scf object is an independent object to the regular scf object which is to be decorated. By doing so, density fitting can be applied anytime, anywhere in your script without affecting the exsited scf object. See also: examples/df/00-with_df.py examples/df/01-auxbasis.py ''' lib.num_threads(44) mol = gto.Mole() mol.build( verbose=7, atom=''' C 9.822751 0.713143 0.000000 C 9.822751 -0.713143 0.000000 H 10.769689 -1.246217 0.000000 H 10.769689 1.246217 0.000000 C 8.640499 1.406976 0.000000 C 8.640499 -1.406976 0.000000 C 7.384570 0.724117 0.000000 C 7.384570 -0.724117 0.000000 H 8.636571 2.494304 0.000000 H 8.636571 -2.494304 0.000000 C 6.162609 1.405479 0.000000
def assign_rdm1s(mol: gto.Mole, s: np.ndarray, mo_coeff: Tuple[np.ndarray, np.ndarray], \ mo_occ: np.ndarray, ref: str, pop: str, part: str, multiproc: bool, verbose: int, \ **kwargs: float) -> Tuple[Union[List[np.ndarray], List[List[np.ndarray]]], Union[None, np.ndarray]]: """ this function returns a list of population weights of each spin-orbital on the individual atoms """ # declare nested kernel function in global scope global get_weights # max number of occupied spin-orbs n_spin = max(mol.alpha.size, mol.beta.size) # mol object projected into minao basis if pop == 'iao': pmol = lo.iao.reference_mol(mol) else: pmol = mol # number of atoms natm = pmol.natm # AO labels ao_labels = pmol.ao_labels(fmt=None) # overlap matrix if pop == 'mulliken': ovlp = s else: ovlp = np.eye(pmol.nao_nr()) def get_weights(orb_idx: int): """ this function computes the full set of population weights """ # get orbital orb = mo[:, orb_idx].reshape(mo.shape[0], 1) # orbital-specific rdm1 rdm1_orb = make_rdm1(orb, mocc[orb_idx]) # population weights of rdm1_orb return _population(natm, ao_labels, ovlp, rdm1_orb) # init population weights array weights = [ np.zeros([n_spin, pmol.natm], dtype=np.float64), np.zeros([n_spin, pmol.natm], dtype=np.float64) ] # loop over spin for i, spin_mo in enumerate((mol.alpha, mol.beta)): # get mo coefficients and occupation if pop == 'mulliken': mo = mo_coeff[i][:, spin_mo] elif pop == 'iao': iao = lo.iao.iao(mol, mo_coeff[i][:, spin_mo]) iao = lo.vec_lowdin(iao, s) mo = contract('ki,kl,lj->ij', iao, s, mo_coeff[i][:, spin_mo]) mocc = mo_occ[i][spin_mo] # domain domain = np.arange(spin_mo.size) # execute kernel if multiproc: n_threads = min(domain.size, lib.num_threads()) with mp.Pool(processes=n_threads) as pool: weights[i] = pool.map(get_weights, domain) # type:ignore else: weights[i] = list(map(get_weights, domain)) # type:ignore # closed-shell reference if ref == 'restricted' and mol.spin == 0: weights[i + 1] = weights[i] break # verbose print if 0 < verbose: symbols = [pmol.atom_pure_symbol(i) for i in range(pmol.natm)] print('\n *** partial population weights: ***') print(' spin ' + 'MO ' + ' '.join(['{:}'.format(i) for i in symbols])) for i, spin_mo in enumerate((mol.alpha, mol.beta)): for j in domain: with np.printoptions(suppress=True, linewidth=200, formatter={'float': '{:6.3f}'.format}): print(' {:s} {:>2d} {:}'.format( 'a' if i == 0 else 'b', spin_mo[j], weights[i][j])) # bond-wise partitioning if part == 'bonds': # init population centres array and get threshold centres = [ np.zeros([mol.alpha.size, 2], dtype=np.int), np.zeros([mol.beta.size, 2], dtype=np.int) ] thres = kwargs['thres'] # loop over spin for i, spin_mo in enumerate((mol.alpha, mol.beta)): # loop over orbitals for j in domain: # get sorted indices max_idx = np.argsort(weights[i][j])[::-1] # compute population centres if np.abs(weights[i][j][max_idx[0]]) > thres: # core orbital or lone pair centres[i][j] = np.array([max_idx[0], max_idx[0]], dtype=np.int) else: # valence orbitals centres[i][j] = np.sort( np.array([max_idx[0], max_idx[1]], dtype=np.int)) # closed-shell reference if ref == 'restricted' and mol.spin == 0: centres[i + 1] = centres[i] break # unique and repetitive centres centres_unique = np.array( [np.unique(centres[i], axis=0) for i in range(2)]) rep_idx = [[ np.where((centres[i] == j).all(axis=1))[0] for j in centres_unique[i] ] for i in range(2)] if part in ['atoms', 'eda']: return weights, None else: return rep_idx, centres_unique