def run_pyscf(molecule, run_fci=False, verbose=False, n_frozen_orbital=0, n_cancel_orbital=0, cas_irrep_nocc=None, cas_irrep_ncore=None): # ZZJ CHANGE """ This function runs a pyscf calculation. Args: molecule: An instance of the MolecularData or PyscfMolecularData class. run_scf: Optional boolean to run SCF calculation. run_mp2: Optional boolean to run MP2 calculation. run_cisd: Optional boolean to run CISD calculation. run_ccsd: Optional boolean to run CCSD calculation. run_fci: Optional boolean to FCI calculation. ## NOTICE !!! FCI is changed to only done in the active space --- ZZJ CHANGE verbose: Boolean whether to print calculation results to screen. Returns: molecule: The updated PyscfMolecularData object. Note the attributes of the input molecule are also updated in this function. """ run_scf = True # ZZJ CHANGE scf must be run # Prepare pyscf molecule. pyscf_molecule = prepare_pyscf_molecule(molecule) molecule.n_orbitals = int(pyscf_molecule.nao_nr()) molecule.n_qubits = 2 * molecule.n_orbitals molecule.nuclear_repulsion = float(pyscf_molecule.energy_nuc()) # Run SCF. pyscf_scf = compute_scf(pyscf_molecule) pyscf_scf.verbose = 0 pyscf_scf.run() molecule.hf_energy = float(pyscf_scf.e_tot) if verbose: print('Hartree-Fock energy for {} ({} electrons) is {}.'.format( molecule.name, molecule.n_electrons, molecule.hf_energy)) # Hold pyscf data in molecule. They are required to compute density # matrices and other quantities. molecule._pyscf_data = pyscf_data = {} pyscf_data['mol'] = pyscf_molecule pyscf_data['scf'] = pyscf_scf # Populate fields. molecule.canonical_orbitals = pyscf_scf.mo_coeff.astype(float) molecule.orbital_energies = pyscf_scf.mo_energy.astype(float) # Get integrals. one_body_integrals, two_body_integrals = compute_integrals( pyscf_molecule, pyscf_scf) molecule.one_body_integrals = one_body_integrals molecule.two_body_integrals = two_body_integrals molecule.overlap_integrals = pyscf_scf.get_ovlp() # Run FCI. if run_fci: # pyscf_fci = fci.FCI(pyscf_scf) # pyscf_fci.verbose = 0 # molecule.fci_energy, molecule.fci_wfn = pyscf_fci.kernel() # pyscf_data['fci'] = pyscf_fci # pyscf_data['fci_wfn'] = molecule.fci_wfn nelec = molecule.n_electrons - n_frozen_orbital * 2 norb = molecule.n_orbitals - n_cancel_orbital - n_frozen_orbital pyscf_fci = mcscf.CASCI(pyscf_scf, norb, nelec) pyscf_fci.verbose = 0 if cas_irrep_nocc != None: molecule.active_orbitals = mcscf.caslst_by_irrep( pyscf_fci, pyscf_scf.mo_coeff, cas_irrep_nocc, cas_irrep_ncore) mo = pyscf_fci.sort_mo_by_irrep(cas_irrep_nocc, cas_irrep_ncore) frozen_orbitals_0 = [ i for i in range(molecule.active_orbitals[norb - 1] + 1) ] for i in range(len(molecule.active_orbitals)): molecule.active_orbitals[i] -= 1 frozen_orbitals_0[molecule.active_orbitals[i]] = -1 molecule.frozen_orbitals = [] for orb in frozen_orbitals_0: if orb != -1: molecule.frozen_orbitals.append(orb) if n_frozen_orbital == len(molecule.frozen_orbitals): break pyscf_data['active_orbitals'] = molecule.active_orbitals pyscf_data['frozen_orbitals'] = molecule.frozen_orbitals else: mo = None molecule.active_orbitals = [ i for i in range(n_frozen_orbital, n_frozen_orbital + norb) ] molecule.frozen_orbitals = [i for i in range(n_frozen_orbital)] fci_result = pyscf_fci.kernel(mo) pyscf_fci.analyze() molecule.fci_energy = fci_result[0] molecule.fci_wfn = fci_result[2] if verbose: print('FCI energy for {} ({} electrons) is {}.'.format( molecule.name, molecule.n_electrons, molecule.fci_energy)) # Return updated molecule instance. pyscf_molecular_data = PyscfMolecularData.__new__(PyscfMolecularData) pyscf_molecular_data.__dict__.update(molecule.__dict__) pyscf_molecular_data.save() return pyscf_molecular_data
def run_pyscf(molecule, run_scf=True, run_mp2=False, run_cisd=False, run_ccsd=False, run_fci=False, verbose=False): """ This function runs a pyscf calculation. Args: molecule: An instance of the MolecularData or PyscfMolecularData class. run_scf: Optional boolean to run SCF calculation. run_mp2: Optional boolean to run MP2 calculation. run_cisd: Optional boolean to run CISD calculation. run_ccsd: Optional boolean to run CCSD calculation. run_fci: Optional boolean to FCI calculation. verbose: Boolean whether to print calculation results to screen. Returns: molecule: The updated PyscfMolecularData object. Note the attributes of the input molecule are also updated in this function. """ # Prepare pyscf molecule. pyscf_molecule = prepare_pyscf_molecule(molecule) molecule.n_orbitals = int(pyscf_molecule.nao_nr()) molecule.n_qubits = 2 * molecule.n_orbitals molecule.nuclear_repulsion = float(pyscf_molecule.energy_nuc()) # Run SCF. pyscf_scf = compute_scf(pyscf_molecule) pyscf_scf.verbose = 0 # Custom properties pyscf_scf.chkfile = 'chkfiles/rohf.chk' pyscf_scf.init_guess = 'chkfile' #pyscf_scf.max_cycle = 1000 pyscf_scf.max_cycle = 0 # Use chkfile pyscf_scf.verbose = 4 pyscf_scf.run() pyscf_scf.analyze() molecule.hf_energy = float(pyscf_scf.e_tot) if verbose: print('Hartree-Fock energy for {} ({} electrons) is {}.'.format( molecule.name, molecule.n_electrons, molecule.hf_energy)) # Hold pyscf data in molecule. They are required to compute density # matrices and other quantities. molecule._pyscf_data = pyscf_data = {} pyscf_data['mol'] = pyscf_molecule pyscf_data['scf'] = pyscf_scf # Populate fields. molecule.canonical_orbitals = pyscf_scf.mo_coeff.astype(float) molecule.orbital_energies = pyscf_scf.mo_energy.astype(float) # Get integrals. # Try to load integrals from file if they exist try: print("Attempting to load integrals...") one_body_integrals = np.load("1e-integrals.npy") two_body_integrals = np.load("2e-integrals.npy") except FileNotFoundError: print("Integrals not found. Recalculating...") one_body_integrals, two_body_integrals = compute_integrals( pyscf_molecule, pyscf_scf) np.save("1e-integrals.npy", one_body_integrals) np.save("2e-integrals.npy", two_body_integrals) print("Integrals loaded") molecule.one_body_integrals = one_body_integrals molecule.two_body_integrals = two_body_integrals molecule.overlap_integrals = pyscf_scf.get_ovlp() # Run MP2. if run_mp2: if molecule.multiplicity != 1: print("WARNING: RO-MP2 is not available in PySCF.") else: pyscf_mp2 = mp.MP2(pyscf_scf) pyscf_mp2.verbose = 0 pyscf_mp2.run() # molecule.mp2_energy = pyscf_mp2.e_tot # pyscf-1.4.4 or higher molecule.mp2_energy = pyscf_scf.e_tot + pyscf_mp2.e_corr pyscf_data['mp2'] = pyscf_mp2 if verbose: print('MP2 energy for {} ({} electrons) is {}.'.format( molecule.name, molecule.n_electrons, molecule.mp2_energy)) # Run CISD. if run_cisd: pyscf_cisd = ci.CISD(pyscf_scf) pyscf_cisd.verbose = 0 pyscf_cisd.run() molecule.cisd_energy = pyscf_cisd.e_tot pyscf_data['cisd'] = pyscf_cisd if verbose: print('CISD energy for {} ({} electrons) is {}.'.format( molecule.name, molecule.n_electrons, molecule.cisd_energy)) # Run CCSD. if run_ccsd: pyscf_ccsd = cc.CCSD(pyscf_scf) pyscf_ccsd.verbose = 0 pyscf_ccsd.run() molecule.ccsd_energy = pyscf_ccsd.e_tot pyscf_data['ccsd'] = pyscf_ccsd if verbose: print('CCSD energy for {} ({} electrons) is {}.'.format( molecule.name, molecule.n_electrons, molecule.ccsd_energy)) # Run FCI. if run_fci: pyscf_fci = fci.FCI(pyscf_molecule, pyscf_scf.mo_coeff) pyscf_fci.verbose = 0 molecule.fci_energy = pyscf_fci.kernel()[0] pyscf_data['fci'] = pyscf_fci if verbose: print('FCI energy for {} ({} electrons) is {}.'.format( molecule.name, molecule.n_electrons, molecule.fci_energy)) # Return updated molecule instance. print("Ending pyscf...") pyscf_molecular_data = PyscfMolecularData.__new__(PyscfMolecularData) pyscf_molecular_data.__dict__.update(molecule.__dict__) print("Saving...") #pyscf_molecular_data.save() print("Saved") return pyscf_molecular_data