def test_cderi_to_save(self): with open(os.devnull, 'w') as f: ftmp = tempfile.NamedTemporaryFile() dfobj = df.DF(mol) dfobj.auxmol = df.addons.make_auxmol(mol, 'weigend') dfobj.verbose = 5 dfobj.stdout = f dfobj._cderi_to_save = ftmp.name dfobj._cderi = 'abc' dfobj.kernel() eri0 = dfobj.get_eri() dfobj = df.DF(mol) dfobj._cderi = ftmp.name eri1 = dfobj.get_eri() self.assertAlmostEqual(abs(eri0-eri1).max(), 0, 9)
def test_ao2mo(self): dfobj = df.DF(mol) # force DF intermediates to be saved on disk dfobj.max_memory = 0.01 # Initialize _call_count, to test DF.prange function dfobj._call_count = 0 # dfobj.build is called in dfobj.get_naoaux() self.assertEqual(dfobj.get_naoaux(), 116) #dfobj.build() cderi = dfobj._cderi nao = mol.nao_nr() eri0 = dfobj.get_eri() numpy.random.seed(1) mos = numpy.random.random((nao,nao*10)) mos = (mos[:,:5], mos[:,5:11], mos[:,3:9], mos[:,2:4]) mo_eri0 = ao2mo.kernel(eri0, mos) mo_eri1 = dfobj.ao2mo(mos) self.assertAlmostEqual(abs(mo_eri0-mo_eri1).max(), 0, 9) mo = numpy.random.random((nao,nao)) mo_eri0 = ao2mo.kernel(eri0, mo) mo_eri1 = dfobj.ao2mo(mo) self.assertAlmostEqual(abs(mo_eri0-mo_eri1).max(), 0, 9)
def __init__(self, mf, frozen=None): self.mol = mf.mol self._scf = mf self.verbose = self.mol.verbose self.stdout = self.mol.stdout self.max_memory = mf.max_memory self.frozen = frozen #TODO: implement frozen orbs if not (self.frozen is None or self.frozen == 0): raise NotImplementedError # DF-GW must use density fitting integrals if getattr(mf, 'with_df', None): self.with_df = mf.with_df else: self.with_df = df.DF(mf.mol) self.with_df.auxbasis = df.make_auxbasis(mf.mol, mp2fit=True) self._keys.update(['with_df']) ################################################## # don't modify the following attributes, they are not input options self._nocc = None self._nmo = None # self.mo_energy: GW quasiparticle energy, not scf mo_energy self.mo_energy = None self.mo_coeff = mf.mo_coeff self.mo_occ = mf.mo_occ self.sigma = None keys = set(('eta', 'linearized')) self._keys = set(self.__dict__.keys()).union(keys)
def __init__(self, mf, frozen=None, auxbasis=None): self.mol = mf.mol self._scf = mf self.verbose = self.mol.verbose self.stdout = self.mol.stdout self.max_memory = mf.max_memory self.frozen = frozen # DF-RPA must use density fitting integrals if getattr(mf, 'with_df', None): self.with_df = mf.with_df else: self.with_df = df.DF(mf.mol) if auxbasis: self.with_df.auxbasis = auxbasis else: self.with_df.auxbasis = df.make_auxbasis(mf.mol, mp2fit=True) self._keys.update(['with_df']) ################################################## # don't modify the following attributes, they are not input options self._nocc = None self._nmo = None self.mo_energy = mf.mo_energy self.mo_coeff = mf.mo_coeff self.mo_occ = mf.mo_occ self.e_corr = None self.e_hf = None self.e_tot = None
def test_hf_dfgs(self): mf = scf.UHF(mol).run() myadc = adc.ADC(mf) myadc.with_df = df.DF(mol, auxbasis='cc-pvdz-ri') e, t_amp1, t_amp2 = myadc.kernel_gs() self.assertAlmostEqual(e, -0.150979874, 6)
def __init__(self, mf, frozen=0, mo_coeff=None, mo_occ=None): ccsd.CCSD.__init__(self, mf, frozen, mo_coeff, mo_occ) if hasattr(mf, 'with_df') and mf.with_df: self.with_df = mf.with_df else: self.with_df = df.DF(mf.mol) self.with_df.auxbasis = df.make_auxbasis(mf.mol, mp2fit=True) self._keys.update(['with_df'])
def __init__(self, mf, frozen=None, mo_coeff=None, mo_occ=None): mp2.MP2.__init__(self, mf, frozen, mo_coeff, mo_occ) if getattr(mf, 'with_df', None): self.with_df = mf.with_df else: self.with_df = df.DF(mf.mol) self.with_df.auxbasis = df.make_auxbasis(mf.mol, mp2fit=True) self._keys.update(['with_df'])
def test_rsh_get_jk(self): nao = mol.nao_nr() numpy.random.seed(1) dm = numpy.random.random((2,nao,nao)) dfobj = df.DF(mol) vj, vk = dfobj.get_jk(dm, hermi=0, omega=1.1) self.assertAlmostEqual(lib.finger(vj), -181.5033531437091, 4) self.assertAlmostEqual(lib.finger(vk), -37.78854217974532, 4) vj1, vk1 = scf.hf.get_jk(mol, dm, hermi=0, omega=1.1) self.assertAlmostEqual(abs(vj-vj1).max(), 0, 2) self.assertAlmostEqual(abs(vk-vk1).max(), 0, 2)
def __init__(self, mf, frozen=None, mo_energy=None, mo_coeff=None, mo_occ=None): uagf2.UAGF2.__init__(self, mf, frozen=frozen, mo_energy=mo_energy, mo_coeff=mo_coeff, mo_occ=mo_occ) if getattr(mf, 'with_df', None) is not None: self.with_df = mf.with_df else: self.with_df = df.DF(mf.mol) self.with_df.auxbasis = df.make_auxbasis(mf.mol, mp2fit=True) self.allow_lowmem_build = True self._keys.update(['_with_df', 'allow_lowmem_build'])
def __init__(self, mf): self.mol = mf.mol self.verbose = self.mol.verbose self.stdout = self.mol.stdout self.max_memory = mf.max_memory self._scf = mf if hasattr(mf, 'with_df') and mf.with_df: self.with_df = None else: self.with_df = df.DF(mol) self.with_df.auxbasis = df.make_auxbasis(mol, mp2fit=True) self.emp2 = None self.t2 = None
def test_ao2mo(self): dfobj = df.DF(mol) dfobj.build() cderi = dfobj._cderi nao = mol.nao_nr() eri0 = ao2mo.restore(8, numpy.dot(cderi.T, cderi), nao) numpy.random.seed(1) mos = numpy.random.random((nao, nao * 10)) mos = (mos[:, :5], mos[:, 5:11], mos[:, 3:9], mos[:, 2:4]) mo_eri0 = ao2mo.kernel(eri0, mos) mo_eri1 = dfobj.ao2mo(mos) self.assertTrue(numpy.allclose(mo_eri0, mo_eri1))
def test_ea_dfadc3(self): myadc.with_df = df.DF(mol, auxbasis='cc-pvdz-ri') myadc.max_memory = 20 myadc.method = "adc(3)" myadc.method_type = "ea" e, v, p = myadc.kernel(nroots=4) self.assertAlmostEqual(e[0], 0.03349588, 6) self.assertAlmostEqual(e[1], 0.17178726, 6) self.assertAlmostEqual(e[2], 0.17734579, 6) self.assertAlmostEqual(e[3], 0.20135255, 6) self.assertAlmostEqual(p[0], 0.9364865, 6) self.assertAlmostEqual(p[1], 0.98406359, 6) self.assertAlmostEqual(p[2], 0.77604385, 6) self.assertAlmostEqual(p[3], 0.20823964, 6)
def test_ip_dfadc3_dif_aux_basis(self): myadc.with_df = df.DF(mol, auxbasis='aug-cc-pvdz-ri') myadc.max_memory = 2 myadc.method = "adc(3)" myadc.method_type = "ip" e, v, p = myadc.kernel(nroots=3) e_corr = myadc.e_corr self.assertAlmostEqual(e_corr, -0.16330973, 6) self.assertAlmostEqual(e[0], 0.45707428, 6) self.assertAlmostEqual(e[1], 0.46818375, 6) self.assertAlmostEqual(e[2], 0.55652918, 6) self.assertAlmostEqual(p[0], 0.93869064, 6) self.assertAlmostEqual(p[1], 0.58692581, 6) self.assertAlmostEqual(p[2], 0.35111056, 6)
def test_hf_dfadc3_ip(self): mf = scf.UHF(mol).run() myadc = adc.ADC(mf) myadc.with_df = df.DF(mol, auxbasis='aug-cc-pvdz-ri') myadc.method = "adc(3)" e, v, p = myadc.kernel(nroots=3) e_corr = myadc.e_corr self.assertAlmostEqual(e_corr, -0.1633223874, 6) self.assertAlmostEqual(e[0], 0.45707376, 6) self.assertAlmostEqual(e[1], 0.46818480, 6) self.assertAlmostEqual(e[2], 0.55652975, 6) self.assertAlmostEqual(p[0], 0.93868596, 6) self.assertAlmostEqual(p[1], 0.58692425, 6) self.assertAlmostEqual(p[2], 0.35110754, 6)
def test_rdf_rhf_eng(self): mol = gto.Mole() mol.atom = """ N 0. 0. 0. H 1.5 0. 0.2 H 0.1 1.2 0. H 0. 0. 1. """ mol.basis = "cc-pVDZ" mol.verbose = 0 mol.build() mf_scf = scf.RHF(mol).density_fit(auxbasis="cc-pVDZ-jkfit").run() mf_mp2 = mp.MP2(mf_scf) mf_mp2.with_df = df.DF(mol, auxbasis="cc-pVDZ-ri") mf_mp2.run() aux_ri = df.make_auxmol(mol, "cc-pVDZ-ri") config = {"scf_eng": mf_scf, "aux_ri": aux_ri} helper = GradDFMP2(config) assert np.allclose(helper.eng, mf_mp2.e_tot, rtol=1e-10, atol=1e-12)
def test_dfhf_dfadc_gs(self): myadc.with_df = df.DF(mol, auxbasis='cc-pvdz-ri') e, t_amp1, t_amp2 = myadc.kernel_gs() self.assertAlmostEqual(e, -0.3108102956, 6)
def density_fit(casscf, auxbasis=None, with_df=None): '''Generate DF-CASSCF for given CASSCF object. It is done by overwriting three CASSCF member functions: * casscf.ao2mo which generates MO integrals * casscf.get_veff which generate JK from core density matrix * casscf.get_jk which Args: casscf : an CASSCF object Kwargs: auxbasis : str or basis dict Same format to the input attribute mol.basis. If auxbasis is None, auxiliary basis based on AO basis (if possible) or even-tempered Gaussian basis will be used. Returns: An CASSCF object with a modified J, K matrix constructor which uses density fitting integrals to compute J and K Examples: >>> mol = gto.M(atom='H 0 0 0; F 0 0 1', basis='ccpvdz', verbose=0) >>> mf = scf.RHF(mol) >>> mf.scf() >>> mc = DFCASSCF(mf, 4, 4) -100.05994191570504 ''' casscf_class = casscf.__class__ if with_df is None: if (getattr(casscf._scf, 'with_df', None) and (auxbasis is None or auxbasis == casscf._scf.with_df.auxbasis)): with_df = casscf._scf.with_df else: with_df = df.DF(casscf.mol) with_df.max_memory = casscf.max_memory with_df.stdout = casscf.stdout with_df.verbose = casscf.verbose with_df.auxbasis = auxbasis class DFCASSCF(casscf_class, _DFCASSCF): def __init__(self): self.__dict__.update(casscf.__dict__) #self.grad_update_dep = 0 self.with_df = with_df self._keys = self._keys.union(['with_df']) def dump_flags(self, verbose=None): casscf_class.dump_flags(self, verbose) logger.info( self, 'DFCASCI/DFCASSCF: density fitting for JK matrix ' 'and 2e integral transformation') return self def ao2mo(self, mo_coeff=None): if self.with_df and 'CASSCF' in casscf_class.__name__: return _ERIS(self, mo_coeff, self.with_df) else: return casscf_class.ao2mo(self, mo_coeff) def get_h2eff(self, mo_coeff=None): # For CASCI if self.with_df: if mo_coeff is None: mo_coeff = self.mo_coeff[:, self.ncore:self.ncore + self.ncas] elif mo_coeff.shape[1] != self.ncas: mo_coeff = mo_coeff[:, self.ncore:self.ncore + self.ncas] return self.with_df.ao2mo(mo_coeff) else: return casscf_class.get_h2eff(self, mo_coeff) # Modify get_veff for JK matrix of core density because get_h1eff calls # self.get_veff to generate core JK def get_veff(self, mol=None, dm=None, hermi=1): if dm is None: mocore = self.mo_coeff[:, :self.ncore] dm = numpy.dot(mocore, mocore.T) * 2 vj, vk = self.get_jk(mol, dm, hermi) return vj - vk * .5 # We don't modify self._scf because it changes self.h1eff function. # We only need approximate jk for self.update_jk_in_ah def get_jk(self, mol, dm, hermi=1): if self.with_df: return self.with_df.get_jk(dm, hermi=hermi) else: return casscf_class.get_jk(self, mol, dm, hermi) def _exact_paaa(self, mo, u, out=None): if self.with_df: nmo = mo.shape[1] ncore = self.ncore ncas = self.ncas nocc = ncore + ncas mo1 = numpy.dot(mo, u) mo1_cas = mo1[:, ncore:nocc] paaa = self.with_df.ao2mo([mo1, mo1_cas, mo1_cas, mo1_cas], compact=False) return paaa.reshape(nmo, ncas, ncas, ncas) else: return casscf_class._exact_paaa(self, mol, u, out) def nuc_grad_method(self): raise NotImplementedError return DFCASSCF()
def approx_hessian(casscf, auxbasis=None, with_df=None): '''Approximate the orbital hessian with density fitting integrals Note this function has no effects if the input casscf object is DF-CASSCF. It only modifies the orbital hessian of normal CASSCF object. Args: casscf : an CASSCF object Kwargs: auxbasis : str or basis dict Same format to the input attribute mol.basis. The default basis 'weigend+etb' means weigend-coulomb-fit basis for light elements and even-tempered basis for heavy elements. Returns: A CASSCF object with approximated JK contraction for orbital hessian Examples: >>> mol = gto.M(atom='H 0 0 0; F 0 0 1', basis='ccpvdz', verbose=0) >>> mf = scf.RHF(mol) >>> mf.scf() >>> mc = mcscf.approx_hessian(mcscf.CASSCF(mf, 4, 4)) -100.06458716530391 ''' casscf_class = casscf.__class__ if 'CASCI' in str(casscf_class): return casscf # because CASCI does not need orbital optimization if getattr(casscf, 'with_df', None): return casscf if with_df is None: if (getattr(casscf._scf, 'with_df', None) and (auxbasis is None or auxbasis == casscf._scf.with_df.auxbasis)): with_df = casscf._scf.with_df else: with_df = df.DF(casscf.mol) with_df.max_memory = casscf.max_memory with_df.stdout = casscf.stdout with_df.verbose = casscf.verbose if auxbasis is not None: with_df.auxbasis = auxbasis class CASSCF(casscf_class): def __init__(self): self.__dict__.update(casscf.__dict__) #self.grad_update_dep = 0 self.with_df = with_df self._keys = self._keys.union(['with_df']) def dump_flags(self): casscf_class.dump_flags(self) logger.info(self, 'CASSCF: density fitting for orbital hessian') def ao2mo(self, mo_coeff): # the exact integral transformation eris = casscf_class.ao2mo(self, mo_coeff) log = logger.Logger(self.stdout, self.verbose) # Add the approximate diagonal term for orbital hessian t1 = t0 = (time.clock(), time.time()) mo = numpy.asarray(mo_coeff, order='F') nao, nmo = mo.shape ncore = self.ncore eris.j_pc = numpy.zeros((nmo, ncore)) k_cp = numpy.zeros((ncore, nmo)) fmmm = _ao2mo.libao2mo.AO2MOmmm_nr_s2_iltj fdrv = _ao2mo.libao2mo.AO2MOnr_e2_drv ftrans = _ao2mo.libao2mo.AO2MOtranse2_nr_s2 bufs1 = numpy.empty((self.with_df.blockdim, nmo, nmo)) for eri1 in self.with_df.loop(): naux = eri1.shape[0] buf = bufs1[:naux] fdrv(ftrans, fmmm, buf.ctypes.data_as(ctypes.c_void_p), eri1.ctypes.data_as(ctypes.c_void_p), mo.ctypes.data_as(ctypes.c_void_p), ctypes.c_int(naux), ctypes.c_int(nao), (ctypes.c_int * 4)(0, nmo, 0, nmo), ctypes.c_void_p(0), ctypes.c_int(0)) bufd = numpy.einsum('kii->ki', buf) eris.j_pc += numpy.einsum('ki,kj->ij', bufd, bufd[:, :ncore]) k_cp += numpy.einsum('kij,kij->ij', buf[:, :ncore], buf[:, :ncore]) t1 = log.timer_debug1('j_pc and k_pc', *t1) eris.k_pc = k_cp.T.copy() log.timer('ao2mo density fit part', *t0) return eris def get_jk(self, mol, dm, hermi=1): if self.with_df: return self.with_df.get_jk(dm, hermi=hermi) else: return casscf_class.get_jk(self, mol, dm, hermi) return CASSCF()
def density_fit(mf, auxbasis=None, with_df=None, only_dfj=False): '''For the given SCF object, update the J, K matrix constructor with corresponding density fitting integrals. Args: mf : an SCF object Kwargs: auxbasis : str or basis dict Same format to the input attribute mol.basis. If auxbasis is None, optimal auxiliary basis based on AO basis (if possible) or even-tempered Gaussian basis will be used. only_dfj : str Compute Coulomb integrals only and no approximation for HF exchange. Same to RIJONX in ORCA Returns: An SCF object with a modified J, K matrix constructor which uses density fitting integrals to compute J and K Examples: >>> mol = gto.M(atom='H 0 0 0; F 0 0 1', basis='ccpvdz', verbose=0) >>> mf = scf.density_fit(scf.RHF(mol)) >>> mf.scf() -100.005306000435510 >>> mol.symmetry = 1 >>> mol.build(0, 0) >>> mf = scf.density_fit(scf.UHF(mol)) >>> mf.scf() -100.005306000435510 ''' from pyscf import df from pyscf.scf import dhf from pyscf.soscf import newton_ah assert (isinstance(mf, scf.hf.SCF)) if with_df is None: if isinstance(mf, dhf.UHF): with_df = df.DF4C(mf.mol) else: with_df = df.DF(mf.mol) with_df.max_memory = mf.max_memory with_df.stdout = mf.stdout with_df.verbose = mf.verbose with_df.auxbasis = auxbasis mf_class = mf.__class__ if isinstance(mf, _DFHF): if getattr(mf.with_df, 'auxbasis', None) != auxbasis: #logger.warn(mf, 'DF might have been initialized twice.') mf = copy.copy(mf) mf.with_df = with_df mf.only_dfj = only_dfj return mf class DFHF(_DFHF, mf_class): __doc__ = ''' Density fitting SCF class Attributes for density-fitting SCF: auxbasis : str or basis dict Same format to the input attribute mol.basis. The default basis 'weigend+etb' means weigend-coulomb-fit basis for light elements and even-tempered basis for heavy elements. with_df : DF object Set mf.with_df = None to switch off density fitting mode. See also the documents of class %s for other SCF attributes. ''' % mf_class def __init__(self, mf, df, only_dfj): self.__dict__.update(mf.__dict__) self._eri = None self.with_df = df self.only_dfj = only_dfj self._keys = self._keys.union(['with_df', 'only_dfj']) def get_jk(self, mol=None, dm=None, hermi=1, with_j=True, with_k=True, omega=None): if dm is None: dm = self.make_rdm1() if self.with_df and self.only_dfj: vj = vk = None if with_j: vj, vk = self.with_df.get_jk(dm, hermi, True, False, self.direct_scf_tol, omega) if with_k: vk = mf_class.get_jk(self, mol, dm, hermi, False, True, omega)[1] elif self.with_df: vj, vk = self.with_df.get_jk(dm, hermi, with_j, with_k, self.direct_scf_tol, omega) else: vj, vk = mf_class.get_jk(self, mol, dm, hermi, with_j, with_k, omega) return vj, vk # for pyscf 1.0, 1.1 compatibility @property def _cderi(self): naux = self.with_df.get_naoaux() return next(self.with_df.loop(blksize=naux)) @_cderi.setter def _cderi(self, x): self.with_df._cderi = x @property def auxbasis(self): return getattr(self.with_df, 'auxbasis', None) return DFHF(mf, with_df, only_dfj)
def test_denisty_fit_interface(self): mydf = df.DF(mol) mycc1 = ccsd.CCSD(mf).density_fit(auxbasis='ccpvdz-ri', with_df=mydf).run() self.assertAlmostEqual(mycc1.e_tot, -76.119348934346789, 7)
def density_fit(mf, auxbasis=None, with_df=None): '''For the given SCF object, update the J, K matrix constructor with corresponding density fitting integrals. Args: mf : an SCF object Kwargs: auxbasis : str or basis dict Same format to the input attribute mol.basis. If auxbasis is None, optimal auxiliary basis based on AO basis (if possible) or even-tempered Gaussian basis will be used. Returns: An SCF object with a modified J, K matrix constructor which uses density fitting integrals to compute J and K Examples: >>> mol = gto.M(atom='H 0 0 0; F 0 0 1', basis='ccpvdz', verbose=0) >>> mf = scf.density_fit(scf.RHF(mol)) >>> mf.scf() -100.005306000435510 >>> mol.symmetry = 1 >>> mol.build(0, 0) >>> mf = scf.density_fit(scf.UHF(mol)) >>> mf.scf() -100.005306000435510 ''' from pyscf import df from pyscf.scf import dhf from pyscf.soscf import newton_ah assert (isinstance(mf, scf.hf.SCF)) if isinstance(mf, _DFHF): if mf.with_df is None: mf = mf.__class__(mf) elif mf.with_df.auxbasis != auxbasis: if (isinstance(mf, newton_ah._CIAH_SOSCF) and isinstance(mf._scf, _DFHF)): mf.with_df = copy.copy(mf.with_df) mf.with_df.auxbasis = auxbasis else: raise RuntimeError('DFHF has been initialized. ' 'It cannot be initialized twice.') return mf if with_df is None: if isinstance(mf, dhf.UHF): with_df = df.DF4C(mf.mol) else: with_df = df.DF(mf.mol) with_df.max_memory = mf.max_memory with_df.stdout = mf.stdout with_df.verbose = mf.verbose with_df.auxbasis = auxbasis mf_class = mf.__class__ class DFHF(mf_class, _DFHF): __doc__ = ''' Density fitting SCF class Attributes for density-fitting SCF: auxbasis : str or basis dict Same format to the input attribute mol.basis. The default basis 'weigend+etb' means weigend-coulomb-fit basis for light elements and even-tempered basis for heavy elements. with_df : DF object Set mf.with_df = None to switch off density fitting mode. See also the documents of class %s for other SCF attributes. ''' % mf_class def __init__(self, mf): self.__dict__.update(mf.__dict__) self._eri = None self.auxbasis = auxbasis self.direct_scf = False self.with_df = with_df self._keys = self._keys.union(['auxbasis', 'with_df']) def get_jk(self, mol=None, dm=None, hermi=1): if self.with_df: if mol is None: mol = self.mol if dm is None: dm = self.make_rdm1() vj, vk = self.with_df.get_jk(dm, hermi) return vj, vk else: return mf_class.get_jk(self, mol, dm, hermi) def get_j(self, mol=None, dm=None, hermi=1): if self.with_df: if mol is None: mol = self.mol if dm is None: dm = self.make_rdm1() vj = self.with_df.get_jk(dm, hermi, with_k=False)[0] return vj else: return mf_class.get_j(self, mol, dm, hermi) def get_k(self, mol=None, dm=None, hermi=1): if self.with_df: if mol is None: mol = self.mol if dm is None: dm = self.make_rdm1() vk = self.with_df.get_jk(dm, hermi, with_j=False)[1] return vk else: return mf_class.get_k(self, mol, dm, hermi) # _cderi accesser for pyscf 1.0, 1.1 compatibility @property def _cderi(self): return self.with_df._cderi @_cderi.setter def _cderi(self, x): self.with_df._cderi = x return DFHF(mf)
def density_fit(mf, auxbasis=None, with_df=None): '''For the given SCF object, update the J, K matrix constructor with corresponding density fitting integrals. Args: mf : an SCF object Kwargs: auxbasis : str or basis dict Same format to the input attribute mol.basis. If auxbasis is None, optimal auxiliary basis based on AO basis (if possible) or even-tempered Gaussian basis will be used. Returns: An SCF object with a modified J, K matrix constructor which uses density fitting integrals to compute J and K Examples: >>> mol = gto.M(atom='H 0 0 0; F 0 0 1', basis='ccpvdz', verbose=0) >>> mf = scf.density_fit(scf.RHF(mol)) >>> mf.scf() -100.005306000435510 >>> mol.symmetry = 1 >>> mol.build(0, 0) >>> mf = scf.density_fit(scf.UHF(mol)) >>> mf.scf() -100.005306000435510 ''' from pyscf import df from pyscf.scf import dhf mf_class = mf.__class__ if mf_class.__doc__ is None: doc = '' else: doc = mf_class.__doc__ if with_df is None: if isinstance(mf, dhf.UHF): with_df = df.DF4C(mf.mol) else: with_df = df.DF(mf.mol) with_df.max_memory = mf.max_memory with_df.stdout = mf.stdout with_df.verbose = mf.verbose with_df.auxbasis = auxbasis class DFHF(mf_class, _DFHF): __doc__ = doc + \ ''' Attributes for density-fitting SCF: auxbasis : str or basis dict Same format to the input attribute mol.basis. The default basis 'weigend+etb' means weigend-coulomb-fit basis for light elements and even-tempered basis for heavy elements. ''' def __init__(self): self.__dict__.update(mf.__dict__) self.auxbasis = auxbasis self.direct_scf = False self.with_df = with_df self._keys = self._keys.union(['auxbasis', 'with_df']) def get_jk(self, mol=None, dm=None, hermi=1): if self.with_df: if mol is None: mol = self.mol if dm is None: dm = self.make_rdm1() vj, vk = self.with_df.get_jk(dm, hermi) return vj, vk else: return mf_class.get_jk(self, mol, dm, hermi) def get_j(self, mol=None, dm=None, hermi=1): if self.with_df: if mol is None: mol = self.mol if dm is None: dm = self.make_rdm1() vj = self.with_df.get_jk(dm, hermi, with_k=False)[0] return vj else: return mf_class.get_j(self, mol, dm, hermi) def get_k(self, mol=None, dm=None, hermi=1): if self.with_df: if mol is None: mol = self.mol if dm is None: dm = self.make_rdm1() vk = self.with_df.get_jk(dm, hermi, with_j=False)[1] return vk else: return mf_class.get_k(self, mol, dm, hermi) # _cderi accesser for pyscf 1.0, 1.1 compatibility @property def _cderi(self): return self.with_df._cderi @_cderi.setter def _cderi(self, x): self.with_df._cderi = x @property def _tag_df(self): sys.stderr.write( 'WARN: Deprecated attribute ._tag_df will be removed in future release. ' 'It is replaced by attribute .with_df\n') if self.with_df: return True else: return False return DFHF()
# future use, specify the filename in the attribute mf.with_df._cderi_to_save # mf = scf.RHF(mol).density_fit() mf.with_df._cderi_to_save = 'saved_cderi.h5' mf.kernel() # # To load the precomputed CD tensors in another calculation. # See also example/df/40-precompute_df_integrals.py # # mf = scf.RHF(mol).density_fit() # mf.with_df._cderi = '/path/to/saved/tensor/file' # mf.kernel() # # _cderi can be generated in the DF object without the DF-SCF calculations # mydf = df.DF(mol) mydf.auxbasis = df.make_auxbasis(mol) mydf._cderi_to_save = 'saved_cderi.h5' mydf.build() # # DF integral tensor can also be generated through the call to cholesky_eri # function # cderi = df.incore.cholesky_eri(mol, auxbasis='weigend') df.outcore.cholesky_eri(mol, 'saved_cderi.h5', dataname='j3c', auxbasis=df.make_auxbasis(mol))
def test_df_gs(self): mf = scf.RHF(mol).run() myadc.with_df = df.DF(mol, auxbasis='cc-pvdz-ri') e, t_amp1, t_amp2 = myadc.kernel_gs() self.assertAlmostEqual(e, -0.31081009625, 6)
def mol_to_eng_true(mol): mf_scf = scf.RHF(mol).density_fit(auxbasis="cc-pVDZ-jkfit").run() mf_mp2 = mp.MP2(mf_scf) mf_mp2.with_df = df.DF(mol, auxbasis="cc-pVDZ-ri") return mf_mp2.run().e_tot
def density_fit(casscf, auxbasis=None, with_df=None): '''Generate DF-CASSCF for given CASSCF object. It is done by overwriting three CASSCF member functions: * casscf.ao2mo which generates MO integrals * casscf.get_veff which generate JK from core density matrix * casscf.get_jk which Args: casscf : an CASSCF object Kwargs: auxbasis : str or basis dict Same format to the input attribute mol.basis. The default basis 'weigend+etb' means weigend-coulomb-fit basis for light elements and even-tempered basis for heavy elements. Returns: An CASSCF object with a modified J, K matrix constructor which uses density fitting integrals to compute J and K Examples: >>> mol = gto.M(atom='H 0 0 0; F 0 0 1', basis='ccpvdz', verbose=0) >>> mf = scf.RHF(mol) >>> mf.scf() >>> mc = DFCASSCF(mf, 4, 4) -100.05994191570504 ''' casscf_class = casscf.__class__ if with_df is None: if (hasattr(casscf._scf, 'with_df') and (auxbasis is None or auxbasis == casscf._scf.with_df.auxbasis)): with_df = casscf._scf.with_df else: with_df = df.DF(casscf.mol) with_df.max_memory = casscf.max_memory with_df.stdout = casscf.stdout with_df.verbose = casscf.verbose if auxbasis is not None: with_df.auxbasis = auxbasis class CASSCF(casscf_class): def __init__(self): self.__dict__.update(casscf.__dict__) #self.grad_update_dep = 0 self.with_df = with_df self._keys = self._keys.union(['with_df']) def dump_flags(self): casscf_class.dump_flags(self) logger.info(self, 'DFCASCI/DFCASSCF: density fitting for JK matrix and 2e integral transformation') def ao2mo(self, mo_coeff): if self.with_df: return _ERIS(self, mo_coeff, self.with_df) else: return casscf_class.ao2mo(self, mo_coeff) def get_h2eff(self, mo_coeff=None): # For CASCI if self.with_df: mo = numpy.asarray(mo_coeff, order='F') nao, nmo = mo.shape naoaux = self.with_df.get_naoaux() buf = numpy.empty((naoaux,nmo*(nmo+1)//2)) fmmm = _ao2mo._fpointer('AO2MOmmm_nr_s2_s2') fdrv = _ao2mo.libao2mo.AO2MOnr_e2_drv ftrans = _ao2mo._fpointer('AO2MOtranse2_nr_s2') b0 = 0 for eri1 in self.with_df.loop(): naux = eri1.shape[0] fdrv(ftrans, fmmm, buf[b0:b0+naux].ctypes.data_as(ctypes.c_void_p), eri1.ctypes.data_as(ctypes.c_void_p), mo.ctypes.data_as(ctypes.c_void_p), ctypes.c_int(naux), ctypes.c_int(nao), ctypes.c_int(0), ctypes.c_int(nmo), ctypes.c_int(0), ctypes.c_int(nmo), ctypes.c_void_p(0), ctypes.c_int(0)) b0 += naux eri = pyscf.lib.dot(buf.T, buf) return eri else: return casscf_class.get_h2eff(self, mo_coeff) # Modify get_veff for JK matrix of core density because get_h1eff calls # self.get_veff to generate core JK def get_veff(self, mol=None, dm=None, hermi=1): if self.with_df: if dm is None: mocore = self.mo_coeff[:,:self.ncore] dm = numpy.dot(mocore, mocore.T) * 2 vj, vk = self.with_df.get_jk(mol, dm, hermi=hermi) return vj-vk*.5 else: return casscf_class.get_jk(self, mol, dm, hermi) # We don't modify self._scf because it changes self.h1eff function. # We only need approximate jk for self.update_jk_in_ah def get_jk(self, mol, dm, hermi=1): if self.with_df: return self.with_df.get_jk(mol, dm, hermi=hermi) else: return casscf_class.get_jk(self, mol, dm, hermi) def _exact_paaa(self, mo, u, out=None): if self.with_df: nmo = mo.shape[1] ncore = self.ncore ncas = self.ncas nocc = ncore + ncas mo1 = numpy.dot(mo, u) mo1_cas = mo1[:,ncore:nocc] paaa = numpy.zeros((nmo*ncas,ncas*ncas)) moij = numpy.asarray(numpy.hstack((mo1, mo1_cas)), order='F') ijshape = (0, nmo, nmo, nmo+ncas) for eri1 in self.with_df.loop(): bufpa = _ao2mo.nr_e2(eri1, moij, ijshape, 's2', 's1') bufaa = numpy.asarray(buf1[ncore:nocc,:], order='C') pyscf.lib.dot(bufpa.T, bufaa, 1, paaa, 1) return paaa.reshape(nmo,ncas,ncas,ncas) else: return casscf_class._exact_paaa(self, mol, u, out) return CASSCF()
if __name__ == '__main__': from pyscf import scf from pyscf import gto mol = gto.Mole() mol.verbose = 0 mol.atom = [[8, (0., 0., 0.)], [1, (0., -0.757, 0.587)], [1, (0., 0.757, 0.587)]] mol.basis = 'cc-pvdz' mol.build() mf = scf.RHF(mol).run() pt = DFMP2(mf) emp2, t2 = pt.kernel() print(emp2 - -0.204004830285) pt.with_df = df.DF(mol) pt.with_df.auxbasis = 'weigend' emp2, t2 = pt.kernel() print(emp2 - -0.204254500453) mf = scf.density_fit(scf.RHF(mol), 'weigend') mf.kernel() pt = DFMP2(mf) emp2, t2 = pt.kernel() print(emp2 - -0.203986171133) pt.with_df = df.DF(mol) pt.with_df.auxbasis = df.make_auxbasis(mol, mp2fit=True) emp2, t2 = pt.kernel() print(emp2 - -0.203738031827)
ncore = 1 nao, nmo = mf.mo_coeff.shape nocc = mol.nelectron//2 - ncore nvir = nmo - nocc - ncore mo_core = mf.mo_coeff[:,:ncore] mo_occ = mf.mo_coeff[:,ncore:ncore+nocc] mo_vir = mf.mo_coeff[:,ncore+nocc:] co = mo_occ cv = mo_vir eo = mf.mo_energy[ncore:ncore+nocc] ev = mf.mo_energy[ncore+nocc:] lib.logger.info(mf,"* Core orbitals: %d" % ncore) lib.logger.info(mf,"* Virtual orbitals: %d" % (len(ev))) with_df = df.DF(mf.mol) with_df.auxbasis = df.make_auxbasis(mf.mol, mp2fit=True) with_df.kernel() #naux = mf._cderi.shape[0] naux = with_df._cderi.shape[0] dferi = numpy.empty((naux,nao,nao)) for i in range(naux): #dferi[i] = lib.unpack_tril(mf._cderi[i]) dferi[i] = lib.unpack_tril(with_df._cderi[i]) eri_mo = einsum('rj,Qrs->Qjs', co, dferi) eri_mo = einsum('sb,Qjs->Qjb', cv, eri_mo) vv_denom = -ev.reshape(-1,1)-ev t2 = numpy.zeros((nocc,nvir,nocc,nvir)) for i in range(nocc):
mf = scf.RHF(mol).run() myadc = adc.ADC(mf).density_fit('aug-cc-pvdz-ri') myadc.kernel_gs() # Running DF-SCF followed by DF-ADC mf = scf.RHF(mol).density_fit().run() myadc = adc.ADC(mf) myadc.kernel_gs() # Using different auxiliary basis for DF-SCF and DF-ADC mf = scf.RHF(mol).density_fit('aug-cc-pvdz-jkfit').run() myadc = adc.ADC(mf).density_fit('aug-cc-pvdz-ri') myadc.verbose = 6 eip, vip, pip, xip = myadc.kernel() # Alternate way to compute DF-ADC mf = scf.RHF(mol).density_fit('aug-cc-pvdz-jkfit').run() myadc = adc.ADC(mf) myadc.with_df = df.DF(mol, auxbasis='aug-cc-pvdz-ri') myadc.verbose = 6 myadc.method = "adc(3)" myadc.method_type = "ea" eea, vea, pea, xea = myadc.kernel(nroots=3) # Compute properties myadc.compute_properties = True myadc.analyze()
mol = gto.Mole() mol.atom = [['O', (0., 0., 0.)], ['H', (0., -0.757, 0.587)], ['H', (0., 0.757, 0.587)]] mol.basis = 'cc-pvdz' mol.build() mf = scf.RHF(mol).density_fit().run() mycc = cc.CCSD(mf).run() print(mycc.e_corr - -0.2134130020105784) # # Using different auxiliary basis for correlation part # mycc.with_df = df.DF(mol, auxbasis='ccpvdz-ri') mycc.run() print(mycc.e_corr - -0.2134650622862191) print("IP energies... (right eigenvector)") part = None e, v = mycc.ipccsd(nroots=3, partition=part) print(e) print(e[0] - 0.43359796846314946) print(e[1] - 0.51880158734392556) print(e[2] - 0.67828839618227565) print("IP energies... (left eigenvector)") e, lv = mycc.ipccsd(nroots=3, left=True, partition=part) print(e) print(e[0] - 0.43359795868636808)