def run_harOH_DVR(self, plotPhasedWfns=False): """ Runs a harmonic approximation using DVR to be fast over the OH coordinate at every OO value.""" from McUtils.Zachary import finite_difference dvr_1D = DVR("ColbertMiller1D") finite_dict = self.logData.finite_dict(midpoint=True) roos = np.array(list(finite_dict.keys())) potential_array = np.zeros((len(finite_dict), self.NumPts, 2)) energies_array = np.zeros((len(finite_dict), self.desiredEnergies)) wavefunctions_array = np.zeros( (len(finite_dict), self.NumPts, self.desiredEnergies)) for j, n in enumerate(finite_dict): x = Constants.convert(finite_dict[n][:, 0], "angstroms", to_AU=True) min_idx = np.argmin(finite_dict[n][:, 1]) sx = x - x[min_idx] y = finite_dict[n][:, 1] k = finite_difference(sx, y, 2, end_point_precision=0, stencil=5, only_center=True)[0] mini = min(sx) - 1.0 maxi = max(sx) + 1.0 res = dvr_1D.run(potential_function="harmonic_oscillator", k=k, mass=self.massdict["muOOH"], divs=self.NumPts, domain=(mini, maxi), num_wfns=self.desiredEnergies) potential = Constants.convert(res.potential_energy.diagonal(), "wavenumbers", to_AU=False) grid = Constants.convert((res.grid + x[min_idx]), "angstroms", to_AU=False) shiftgrid = (n / 2) + grid potential_array[j, :, 0] = shiftgrid potential_array[j, :, 1] = potential ens = Constants.convert((res.wavefunctions.energies + min(y)), "wavenumbers", to_AU=False) energies_array[j, :] = ens wavefunctions_array[j, :, :] = res.wavefunctions.wavefunctions epsilon_pots = np.column_stack((roos, energies_array[:, :4])) npz_filename = os.path.join( self.DVRdir, f"{self.method}_HarmOHDVR_energies{self.desiredEnergies}.npz") # data saved in wavenumbers/angstroms wavefuns_array = self.wfn_flipper(wavefunctions_array, plotPhasedWfns=plotPhasedWfns, pot_array=potential_array) np.savez(npz_filename, method="harm", potential=potential_array, epsilonPots=epsilon_pots, wfns_array=wavefuns_array) return npz_filename
def run_2D_DVR(self): """Runs 2D DVR over the original 2D potential should take flat xy array, and flat 2D grid in ATOMIC UNITS""" from PyDVR import DVR, ResultsInterpreter from Converter import Constants import os dvr_2D = DVR("ColbertMillerND") xy = np.column_stack((self.grid[0].flatten(), self.grid[1].flatten())) ens = self.ModelHarmonicPotential().flatten() res = dvr_2D.run(potential_grid=np.column_stack((xy, ens)), divs=(100, 100), mass=[self.massdict["muOO"], self.massdict["muOH"]], num_wfns=15, domain=((min(xy[:, 0]), max(xy[:, 0])), (min(xy[:, 1]), max(xy[:, 1]))), results_class=ResultsInterpreter) dvr_grid = Constants.convert(res.grid, "angstroms", to_AU=False) dvr_pot = Constants.convert(res.potential_energy.diagonal(), "wavenumbers", to_AU=False) all_ens = Constants.convert(res.wavefunctions.energies, "wavenumbers", to_AU=False) ResultsInterpreter.wfn_contours(res) oh1oo0 = int(input("OH=1 OO=0 Wavefunction Index: ")) oh1oo1 = int(input("OH=1 OO=1 Wavefunction Index: ")) oh1oo2 = int(input("OH=1 OO=2 Wavefunction Index: ")) ens = np.zeros(4) wfns = np.zeros((4, res.wavefunctions[0].data.shape[0])) for i, wf in enumerate(res.wavefunctions): wfn = wf.data if i == 0: wfns[0] = wfn ens[0] = all_ens[i] elif i == oh1oo0: wfns[1] = wfn ens[1] = all_ens[i] elif i == oh1oo1: wfns[2] = wfn ens[2] = all_ens[i] elif i == oh1oo2: wfns[3] = wfn ens[3] = all_ens[i] else: pass # data saved in wavenumbers/angstrom dvr_dir = os.path.join(self.molecule.mol_dir, "DVR Results") if self.CC: npz_filename = f"{dvr_dir}/HMP_wCC_2D_DVR_OHOO.npz" else: npz_filename = f"{dvr_dir}/HMP_2D_DVR_OHOO.npz" np.savez(npz_filename, grid=[dvr_grid], potential=[dvr_pot], vrwfn_idx=[0, oh1oo0, oh1oo1, oh1oo2], energy_array=ens, wfns_array=wfns) return npz_filename
def run_harOO_DVR(self, OHDVRres=None, plotPhasedWfns=False): """Fits epsilon potentials to a harmonic oscillator and then runs an OO DVR over it""" from McUtils.Zachary import finite_difference dvr_1D = DVR("ColbertMiller1D") OHresults = np.load(OHDVRres) epsi_pots = OHresults["epsilonPots"] potential_array = np.zeros((2, self.NumPts, 2)) energies_array = np.zeros((2, self.desiredEnergies)) wavefunctions_array = np.zeros((2, self.NumPts, self.desiredEnergies)) x = Constants.convert(epsi_pots[:, 0], "angstroms", to_AU=True) for j in np.arange(2): en = Constants.convert(epsi_pots[:, j + 1], "wavenumbers", to_AU=True) minE_idx = np.argmin(en) en_s = en[minE_idx - 2:minE_idx + 3] sx = x - x[minE_idx] k = finite_difference(sx[minE_idx - 2:minE_idx + 3], en_s, 2, end_point_precision=0, stencil=5, only_center=True)[0] mini = min(sx) - 1.0 maxi = max(sx) + 0.5 res = dvr_1D.run(potential_function="harmonic_oscillator", k=k, mass=self.massdict["muOO"], divs=self.NumPts, domain=(mini, maxi), num_wfns=self.desiredEnergies) potential = Constants.convert(res.potential_energy.diagonal() + en[minE_idx], "wavenumbers", to_AU=False) potential_array[j, :, 0] = Constants.convert( (res.grid + x[minE_idx]), "angstroms", to_AU=False) potential_array[j, :, 1] = potential ens = Constants.convert(res.wavefunctions.energies + en[minE_idx], "wavenumbers", to_AU=False) energies_array[j, :] = ens wavefunctions_array[j, :, :] = res.wavefunctions.wavefunctions npz_filename = os.path.join( self.DVRdir, f"{self.method}_harmOODVR_w{OHresults['method']}OHDVR_energies{self.desiredEnergies}.npz" ) # data saved in wavenumbers/angstroms wavefuns_array = self.wfn_flipper(wavefunctions_array, plotPhasedWfns=plotPhasedWfns, pot_array=potential_array) np.savez(npz_filename, potential=potential_array, energy_array=energies_array, wfns_array=wavefuns_array) return npz_filename
def run_2D_DVR(self): """Runs 2D DVR over the original 2D potential""" dvr_2D = DVR("ColbertMillerND") npz_filename = os.path.join(self.DVRdir, f"{self.method}_2D_DVR.npz") twoD_grid = self.logData.rawenergies xy = Constants.convert(twoD_grid[:, :2], "angstroms", to_AU=True) en = twoD_grid[:, 2] en[en > 0.228] = 0.228 # set stricter limit res = dvr_2D.run(potential_grid=np.column_stack((xy, twoD_grid[:, 2])), divs=(100, 100), mass=[self.massdict["muOO"], self.massdict["muOOH"]], num_wfns=15, domain=((min(xy[:, 0]), max(xy[:, 0])), (min(xy[:, 1]), max(xy[:, 1]))), results_class=ResultsInterpreter) dvr_grid = Constants.convert(res.grid, "angstroms", to_AU=False) dvr_pot = Constants.convert(res.potential_energy.diagonal(), "wavenumbers", to_AU=False) all_ens = Constants.convert(res.wavefunctions.energies, "wavenumbers", to_AU=False) ResultsInterpreter.wfn_contours(res) oh1oo0 = int(input("OH=1 OO=0 Wavefunction Index: ")) oh1oo1 = int(input("OH=1 OO=1 Wavefunction Index: ")) oh1oo2 = int(input("OH=1 OO=2 Wavefunction Index: ")) ens = np.zeros(4) wfns = np.zeros((4, res.wavefunctions[0].data.shape[0])) for i, wf in enumerate(res.wavefunctions): wfn = wf.data if i == 0: wfns[0] = wfn ens[0] = all_ens[i] elif i == oh1oo0: wfns[1] = wfn ens[1] = all_ens[i] elif i == oh1oo1: wfns[2] = wfn ens[2] = all_ens[i] elif i == oh1oo2: wfns[3] = wfn ens[3] = all_ens[i] else: pass # data saved in wavenumbers/angstroms np.savez(npz_filename, grid=[dvr_grid], potential=[dvr_pot], vrwfn_idx=[0, oh1oo0, oh1oo1, oh1oo2], energy_array=ens, wfns_array=wfns) return npz_filename
def run_OO_DVR(self, OHDVRres=None, plotPhasedWfns=False): """Runs OO DVR over the epsilon potentials""" from PotentialHandlers import Potentials1D dvr_1D = DVR("ColbertMiller1D") OHresults = np.load(OHDVRres) epsi_pots = OHresults["epsilonPots"] potential_array = np.zeros((2, self.NumPts, 2)) energies_array = np.zeros((2, self.desiredEnergies)) wavefunctions_array = np.zeros((2, self.NumPts, self.desiredEnergies)) x = Constants.convert(epsi_pots[:, 0], "angstroms", to_AU=True) mini = min(x) - 0.3 maxi = max(x) + 0.15 for j in np.arange(2): en = Constants.convert(epsi_pots[:, j + 1], "wavenumbers", to_AU=True) res = dvr_1D.run(potential_function=Potentials1D().potlint(x, en), mass=self.massdict["muOO"], divs=self.NumPts, domain=(mini, maxi), num_wfns=self.desiredEnergies) potential = Constants.convert(res.potential_energy.diagonal(), "wavenumbers", to_AU=False) grid = Constants.convert(res.grid, "angstroms", to_AU=False) potential_array[j, :, 0] = grid potential_array[j, :, 1] = potential min_idx = np.argmin(potential) print(j, grid[min_idx], potential[min_idx]) ens = Constants.convert(res.wavefunctions.energies, "wavenumbers", to_AU=False) print(j, ens) energies_array[j, :] = ens wavefunctions_array[j, :, :] = res.wavefunctions.wavefunctions npz_filename = os.path.join( self.DVRdir, f"{self.method}_OODVR_w{OHresults['method']}OHDVR_energies{self.desiredEnergies}.npz" ) # data saved in wavenumbers/angstroms wavefuns_array = self.wfn_flipper(wavefunctions_array, plotPhasedWfns=plotPhasedWfns, pot_array=potential_array) np.savez(npz_filename, potential=potential_array, energy_array=energies_array, wfns_array=wavefuns_array) return npz_filename
def run_anharOH_DVR(self, plotPhasedWfns=False): """ Runs anharmonic DVR over the OH coordinate at every OO value.""" from PotentialHandlers import Potentials1D dvr_1D = DVR("ColbertMiller1D") cut_dict = self.logData.cut_dictionary() roos = np.array(list(cut_dict.keys())) potential_array = np.zeros((len(cut_dict), self.NumPts, 2)) energies_array = np.zeros((len(cut_dict), self.desiredEnergies)) wavefunctions_array = np.zeros( (len(cut_dict), self.NumPts, self.desiredEnergies)) for j, n in enumerate(cut_dict): x = Constants.convert(cut_dict[n][:, 0], "angstroms", to_AU=True) mini = min(x) - 0.3 maxi = max(x) + 0.3 en = cut_dict[n][:, 1] res = dvr_1D.run(potential_function=Potentials1D().potlint(x, en), mass=self.massdict["muOOH"], divs=self.NumPts, domain=(mini, maxi), num_wfns=self.desiredEnergies) potential = Constants.convert(res.potential_energy.diagonal(), "wavenumbers", to_AU=False) grid = Constants.convert(res.grid, "angstroms", to_AU=False) # shiftgrid = (n/2) + grid potential_array[j, :, 0] = grid # shiftgrid potential_array[j, :, 1] = potential ens = Constants.convert(res.wavefunctions.energies, "wavenumbers", to_AU=False) energies_array[j, :] = ens wavefunctions_array[j, :, :] = res.wavefunctions.wavefunctions epsilon_pots = np.column_stack((roos, energies_array[:, :4])) npz_filename = os.path.join( self.DVRdir, f"{self.method}_AnharmOHDVR_energies{self.desiredEnergies}.npz") # data saved in wavenumbers/angstroms wavefuns_array = self.wfn_flipper(wavefunctions_array, plotPhasedWfns=plotPhasedWfns, pot_array=potential_array) np.savez(npz_filename, method="anharm", potential=potential_array, epsilonPots=epsilon_pots, wfns_array=wavefuns_array) return npz_filename
import glob as glob import matplotlib.pyplot as plt H = 1.007825 O = 15.994915 avo = 6.02213670000e23 me = 9.109383560000e-28 mO = (O / avo) / me mH = (H / avo) / me muOH = ((2*mO)*mH)/((2*mO)+mH) muOO = mO/2 angtobohr = 1.88973 main_dir = os.path.dirname(os.path.dirname(__file__)) scan_dir = os.path.join(main_dir, '2D Scans') dvr_2D = DVR("ColbertMillerND") def regular_grid(grid, vals, interp_kind='cubic', fillvalues=False, plot=False): import matplotlib.pyplot as plt from scipy import interpolate x = grid[:, 0] xvals = np.unique(x) xyzz = np.column_stack((x, grid[:, 1], vals)) slices = [xyzz[x == xv] for xv in xvals] maxx = max(len(slIce) for slIce in slices) idx = np.argmax([len(slIce) for slIce in slices]) rnge = sorted(slices[idx][:, 1]) sgrid = np.empty((0, 3)) for slICE in slices: slICE = slICE[slICE[:, 1].argsort()]
def test_energies_3D(self): dvr_3D = DVR("ColbertMillerND") res = dvr_3D.run(potential_function=self.ho_3D, domain=((-5, 5),)*3, divs=(15,)*3) # print(res[0][:5], file=sys.stderr)gg self.assertIsInstance(res[0], np.ndarray)
def test_energies_2D(self): dvr_2D = DVR("ColbertMillerND") res = dvr_2D.run(potential_function=self.ho_2D, divs=(25, 25)) # print(res[0][:5], file=sys.stderr) self.assertIsInstance(res[0], np.ndarray)
def test_energies_1D(self): dvr_1D = DVR("ColbertMiller1D") e, wf = dvr_1D.run(potential_function=self.ho, divs=150) # print(e[:5], file=sys.stderr) self.assertIsInstance(e, np.ndarray)
def test_1D(self): dvr_1D = DVR("ColbertMiller1D") pot = dvr_1D.run(potential_function=self.ho, result='potential_energy') self.assertIsInstance(pot, np.ndarray)
import matplotlib.pyplot as plt from PyDVR.DVR import * from McUtils.Plots import ContourPlot from scipy import interpolate import eckartRotation as eckin from GaussianHandler import LogInterpreter import glob as glob """Messy implementation of 2D DVR used for checks of adiabatic approximation, The approximation is good. But all of this code is complete crap.""" main_dir = os.path.dirname(os.path.dirname(__file__)) dvr_2D = DVR("ColbertMillerND") H = 1.007825 O = 15.994915 avo = 6.02213670000e23 me = 9.109383560000e-28 mO = (O / avo) / me mH = (H / avo) / me muOH = ((2 * mO) * mH) / ((2 * mO) + mH) muOO = mO / 2 scan_dir = os.path.join(main_dir, '2D Scans') dat = np.loadtxt(os.path.join(scan_dir, '2Dgrid_rigid_har_new.dat')) dat[:, :2] *= 1.88973 dat[:, 2] -= min(dat[:, 2]) big_x = np.arange( min(dat[:, 0]) - (0.3), max(dat[:, 0]) + (0.15), (0.06 * 1.88973)) big_y = np.arange( min(dat[:, 1]) - (0.3), max(dat[:, 1]) + (0.15), (0.06 * 1.88973))