Пример #1
0
def test_ORD_RPA_singlet_BC2H4_cation_HF_STO3G():

    ref = BC2H4_cation_HF_STO3G_RPA_singlet_nwchem

    pyscfmol = molecules.molecule_bc2h4_cation_sto3g()
    pyscfmol.build()

    mf = pyscf.scf.RHF(pyscfmol)
    mf.scf()

    C = utils.fix_mocoeffs_shape(mf.mo_coeff)
    E = utils.fix_moenergies_shape(mf.mo_energy)
    occupations = occupations_from_pyscf_mol(pyscfmol, C)

    frequencies = [0.0, 0.001, 0.0773178, 0.128347]
    ord_solver = optrot.ORD(
        Program.PySCF,
        pyscfmol,
        cphf.CPHF(solvers.ExactInv(C, E, occupations)),
        C,
        E,
        occupations,
        frequencies=frequencies,
        do_dipvel=False,
    )
    ord_solver.form_operators()
    ord_solver.run(hamiltonian=Hamiltonian.RPA, spin=Spin.singlet)
    ord_solver.form_results()

    print("Polarizabilities")
    assert len(frequencies) == len(ord_solver.polarizabilities)
    thresh = 5.0e-4
    for idxf, frequency in enumerate(frequencies):
        ref_polar = ref[frequency]["polar"]
        res_polar = ord_solver.polarizabilities[idxf]
        abs_diff = abs(res_polar - ref_polar)
        print(idxf, frequency)
        print(res_polar)
        print(abs_diff)
        assert (abs_diff < thresh).all()

    print(r"\beta(\omega)")
    thresh = 5.0e-2
    for idxf, frequency in enumerate(frequencies):
        if "orbeta" in ref[frequency]:
            ref_beta = ref[frequency]["orbeta"]
            # TODO why no speed of light?
            # TODO why the (1/2)?
            res_beta = -(0.5 /
                         frequency) * ord_solver.driver.results[idxf][3:6, 0:3]
            abs_diff = abs(res_beta - ref_beta)
            print(idxf, frequency)
            print(res_beta)
            print(abs_diff)
            assert (abs_diff < thresh).all()
Пример #2
0
def test_ECD_RPA_singlet_BC2H4_cation_HF_STO3G() -> None:

    ref = BC2H4_cation_HF_STO3G_RPA_singlet_nwchem
    nroots = ref["nroots"]

    mol = molecules.molecule_bc2h4_cation_sto3g()
    mol.build()

    mf = pyscf.scf.RHF(mol)
    mf.scf()

    C = utils.fix_mocoeffs_shape(mf.mo_coeff)
    E = utils.fix_moenergies_shape(mf.mo_energy)
    occupations = occupations_from_pyscf_mol(mol, C)

    ecd_dipvel_rpa = ecd.ECD(
        Program.PySCF,
        mol,
        td.TDHF(solvers.ExactDiagonalizationSolver(C, E, occupations)),
        C,
        E,
        occupations,
        do_dipvel=True,
    )
    ecd_dipvel_rpa.form_operators()
    ecd_dipvel_rpa.run(hamiltonian=Hamiltonian.RPA, spin=Spin.singlet)
    ecd_dipvel_rpa.form_results()

    print("excitation energies")
    ref_etenergies = np.array(ref["etenergies"])
    res_etenergies = ecd_dipvel_rpa.driver.solver.eigvals.real[:nroots]
    print("ref, res")
    for refval, resval in zip(ref_etenergies, res_etenergies):
        print(refval, resval)
    thresh = 2.5e-7
    for i in range(nroots):
        abs_diff = abs(ref_etenergies[i] - res_etenergies[i])
        assert abs_diff < thresh

    print("dipole (length) oscillator strengths")
    ref_etoscslen = np.array(ref["etoscslen"])
    res_etoscslen = ecd_dipvel_rpa.driver.solver.operators[
        1].total_oscillator_strengths[:nroots]
    print("ref, res")
    for refval, resval in zip(ref_etoscslen, res_etoscslen):
        print(refval, resval)
    thresh = 1.0e-5
    for i in range(nroots):
        abs_diff = abs(ref_etoscslen[i] - res_etoscslen[i])
        assert abs_diff < thresh

    # TODO
    print("TODO dipole (mixed length/velocity) oscillator strengths")

    # TODO
    print("TODO dipole (velocity) oscillator strengths")
    ref_etoscsvel = np.array(ref["etoscsvel"])
    res_etoscsvel = ecd_dipvel_rpa.driver.solver.operators[
        2].total_oscillator_strengths[:nroots]
    # print('ref, res')
    # for refval, resval in zip(ref_etoscsvel, res_etoscsvel):
    #     print(refval, resval)
    # print(ref_etoscsvel / res_etoscsvel)
    # print(res_etoscsvel / ref_etoscsvel)

    print("rotatory strengths (length)")
    ref_etrotstrlen = np.array(ref["etrotstrlen"])
    res_etrotstrlen = ecd_dipvel_rpa.rotational_strengths_diplen[:nroots]
    print("ref, res")
    for refval, resval in zip(ref_etrotstrlen, res_etrotstrlen):
        print(refval, resval)
    # TODO unlike other quantities, the error isn't uniformly
    # distributed among the roots; how should this be handled?
    thresh = 1.5e1
    for i in range(nroots):
        abs_diff = abs(ref_etrotstrlen[i] - res_etrotstrlen[i])
        assert abs_diff < thresh

    print("rotatory strengths (velocity)")
    ref_etrotstrvel = np.array(ref["etrotstrvel"])
    res_etrotstrvel = ecd_dipvel_rpa.rotational_strengths_dipvel[:nroots]
    print("ref, res")
    for refval, resval in zip(ref_etrotstrvel, res_etrotstrvel):
        print(refval, resval)
    thresh = 1.0e-2
    for i in range(nroots):
        abs_diff = abs(ref_etrotstrvel[i] - res_etrotstrvel[i])
        assert abs_diff < thresh
Пример #3
0
def test_ECD_RPA_singlet_BC2H4_cation_HF_STO3G():

    ref = BC2H4_cation_HF_STO3G_RPA_singlet_nwchem
    nroots = ref["nroots"]

    mol = molecules.molecule_bc2h4_cation_sto3g()
    mol.build()

    mf = pyscf.scf.RHF(mol)
    mf.scf()

    C = utils.fix_mocoeffs_shape(mf.mo_coeff)
    E = utils.fix_moenergies_shape(mf.mo_energy)
    occupations = utils.occupations_from_pyscf_mol(mol, C)

    ecd_dipvel_rpa = ecd.ECD(Program.PySCF, mol, C, E, occupations, do_dipvel=True)
    ecd_dipvel_rpa.form_operators()
    ecd_dipvel_rpa.run(hamiltonian="rpa", spin="singlet")
    ecd_dipvel_rpa.form_results()

    print("excitation energies")
    ref_etenergies = np.array(ref["etenergies"])
    res_etenergies = ecd_dipvel_rpa.driver.solver.eigvals.real[:nroots]
    print("ref, res")
    for refval, resval in zip(ref_etenergies, res_etenergies):
        print(refval, resval)
    thresh = 1.0e-7
    for i in range(nroots):
        abs_diff = abs(ref_etenergies[i] - res_etenergies[i])
        assert abs_diff < thresh

    print("dipole (length) oscillator strengths")
    ref_etoscslen = np.array(ref["etoscslen"])
    res_etoscslen = ecd_dipvel_rpa.driver.solver.operators[1].total_oscillator_strengths[
        :nroots
    ]
    print("ref, res")
    for refval, resval in zip(ref_etoscslen, res_etoscslen):
        print(refval, resval)
    thresh = 1.0e-5
    for i in range(nroots):
        abs_diff = abs(ref_etoscslen[i] - res_etoscslen[i])
        assert abs_diff < thresh

    # TODO
    print("TODO dipole (mixed length/velocity) oscillator strengths")

    # TODO
    print("TODO dipole (velocity) oscillator strengths")
    ref_etoscsvel = np.array(ref["etoscsvel"])
    res_etoscsvel = ecd_dipvel_rpa.driver.solver.operators[2].total_oscillator_strengths[
        :nroots
    ]
    # print('ref, res')
    # for refval, resval in zip(ref_etoscsvel, res_etoscsvel):
    #     print(refval, resval)
    # print(ref_etoscsvel / res_etoscsvel)
    # print(res_etoscsvel / ref_etoscsvel)

    print("rotatory strengths (length)")
    ref_etrotstrlen = np.array(ref["etrotstrlen"])
    res_etrotstrlen = ecd_dipvel_rpa.rotational_strengths_diplen[:nroots]
    print("ref, res")
    for refval, resval in zip(ref_etrotstrlen, res_etrotstrlen):
        print(refval, resval)
    # TODO unlike other quantities, the error isn't uniformly
    # distributed among the roots; how should this be handled?
    thresh = 1.5e1
    for i in range(nroots):
        abs_diff = abs(ref_etrotstrlen[i] - res_etrotstrlen[i])
        assert abs_diff < thresh

    print("rotatory strengths (velocity)")
    ref_etrotstrvel = np.array(ref["etrotstrvel"])
    res_etrotstrvel = ecd_dipvel_rpa.rotational_strengths_dipvel[:nroots]
    print("ref, res")
    for refval, resval in zip(ref_etrotstrvel, res_etrotstrvel):
        print(refval, resval)
    thresh = 1.0e-2
    for i in range(nroots):
        abs_diff = abs(ref_etrotstrvel[i] - res_etrotstrvel[i])
        assert abs_diff < thresh

    # with open(os.path.join(refdir, 'BC2H4_cation', 'nwchem_singlet_rpa_velocity_root.str')) as fh:
    #     ref_str = fh.read()
    # res_str = ecd_dipvel_rpa.print_results_nwchem()
    # assert res_str == ref_str
    # print(ecd_dipvel_rpa.print_results_nwchem())
    # print(ecd_dipvel_rpa.print_results_orca())
    # print(ecd_dipvel_rpa.print_results_qchem())

    # tmom_diplen = ecd_dipvel_rpa.driver.solver.operators[1].transition_moments
    # tmom_dipvel = ecd_dipvel_rpa.driver.solver.operators[2].transition_moments
    # print(tmom_diplen)
    # print('dipole')
    # for i in range(nroots):
    #     print((2 / 3) * res_etenergies[i] * np.dot(tmom_diplen[i], tmom_diplen[i]))
    # print('mixed')
    # for i in range(nroots):
    #     print((2 / 3) * res_etenergies[i] * np.dot(tmom_diplen[i], tmom_dipvel[i]))

    # print('sum rule')
    # print('ref_etoscslen:', sum(ref_etoscslen))
    # print('res_etoscslen:', sum(res_etoscslen))
    # # print('ref_etoscsmix:', sum(ref_etoscsmix))
    # # print('res_etoscsmix:', sum(res_etoscsmix))
    # print('ref_etoscsvel:', sum(ref_etoscsvel))
    # print('res_etoscsvel:', sum(res_etoscsvel))

    return
Пример #4
0
def test_ECD_TDA_singlet_BC2H4_cation_HF_STO3G():

    ref = BC2H4_cation_HF_STO3G_TDA_singlet_orca
    nroots = ref["nroots"]

    mol = molecules.molecule_bc2h4_cation_sto3g()
    mol.build()

    mf = pyscf.scf.RHF(mol)
    mf.scf()

    C = utils.fix_mocoeffs_shape(mf.mo_coeff)
    E = utils.fix_moenergies_shape(mf.mo_energy)
    occupations = utils.occupations_from_pyscf_mol(mol, C)

    ecd_dipvel_tda = ecd.ECD(Program.PySCF, mol, C, E, occupations, do_dipvel=True)
    ecd_dipvel_tda.form_operators()
    ecd_dipvel_tda.run(hamiltonian="tda", spin="singlet")
    ecd_dipvel_tda.form_results()

    print("excitation energies")
    ref_etenergies = np.array(ref["etenergies"])
    res_etenergies = ecd_dipvel_tda.driver.solver.eigvals.real[:nroots]
    print("ref, res")
    for refval, resval in zip(ref_etenergies, res_etenergies):
        print(refval, resval)
    # TODO this might be from ORCA, should use NWChem instead
    thresh = 1.0e-3
    for i in range(nroots):
        abs_diff = abs(ref_etenergies[i] - res_etenergies[i])
        assert abs_diff < thresh

    print("dipole (length) oscillator strengths")
    ref_etoscslen = np.array(ref["etoscslen"])
    res_etoscslen = ecd_dipvel_tda.driver.solver.operators[1].total_oscillator_strengths[
        :nroots
    ]
    print("ref, res")
    for refval, resval in zip(ref_etoscslen, res_etoscslen):
        print(refval, resval)
    thresh = 1.0e-3
    # np.testing.assert_allclose(ref_etoscslen, res_etoscslen)
    for i in range(nroots):
        abs_diff = abs(ref_etoscslen[i] - res_etoscslen[i])
        assert abs_diff < thresh

    # TODO
    print("TODO dipole (mixed length/velocity) oscillator strengths")

    # TODO
    print("TODO dipole (velocity) oscillator strengths")

    print("rotatory strengths (length)")
    ref_etrotstrlen = np.array(ref["etrotstrlen"])
    res_etrotstrlen = ecd_dipvel_tda.rotational_strengths_diplen[:nroots]
    print("ref, res")
    for refval, resval in zip(ref_etrotstrlen, res_etrotstrlen):
        print(refval, resval)
    # TODO unlike other quantities, the error isn't uniformly
    # distributed among the roots; how should this be handled?
    thresh = 1.0e2
    for i in range(nroots):
        abs_diff = abs(ref_etrotstrlen[i] - res_etrotstrlen[i])
        assert abs_diff < thresh

    # print('rotatory strengths (velocity)')
    # ref_etrotstrvel = np.array(ref['etrotstrvel'])
    # res_etrotstrvel = ecd_dipvel_tda.rotational_strengths_dipvel[:nroots]
    # print('ref, res')
    # for refval, resval in zip(ref_etrotstrvel, res_etrotstrvel):
    #     print(refval, resval)
    # thresh = 1.0e-2
    # for i in range(nroots):
    #     abs_diff = abs(ref_etrotstrvel[i] - res_etrotstrvel[i])
    #     assert abs_diff < thresh

    # print(ecd_dipvel_tda.print_results_nwchem())
    # print(ecd_dipvel_tda.print_results_orca())
    # print(ecd_dipvel_tda.print_results_qchem())

    return
Пример #5
0
def test_ORD_RPA_singlet_BC2H4_cation_HF_STO3G():

    ref = BC2H4_cation_HF_STO3G_RPA_singlet_nwchem

    pyscfmol = molecules.molecule_bc2h4_cation_sto3g()
    pyscfmol.build()

    mf = pyscf.scf.RHF(pyscfmol)
    mf.scf()

    C = utils.fix_mocoeffs_shape(mf.mo_coeff)
    E = utils.fix_moenergies_shape(mf.mo_energy)
    occupations = utils.occupations_from_pyscf_mol(pyscfmol, C)

    frequencies = [0.0, 0.001, 0.0773178, 0.128347]
    ord_solver = optrot.ORD(
        Program.PySCF,
        pyscfmol,
        C,
        E,
        occupations,
        frequencies=frequencies,
        do_dipvel=False,
    )
    ord_solver.form_operators()
    ord_solver.run(hamiltonian="rpa", spin="singlet")
    ord_solver.form_results()

    print("Polarizabilities")
    assert len(frequencies) == len(ord_solver.polarizabilities)
    thresh = 5.0e-4
    for idxf, frequency in enumerate(frequencies):
        ref_polar = ref[frequency]["polar"]
        res_polar = ord_solver.polarizabilities[idxf]
        abs_diff = abs(res_polar - ref_polar)
        print(idxf, frequency)
        print(res_polar)
        print(abs_diff)
        assert (abs_diff < thresh).all()

    print(r"\beta(\omega)")
    thresh = 5.0e-2
    for idxf, frequency in enumerate(frequencies):
        if "orbeta" in ref[frequency]:
            ref_beta = ref[frequency]["orbeta"]
            # TODO why no speed of light?
            # TODO why the (1/2)?
            res_beta = -(0.5 / frequency) * ord_solver.driver.results[idxf][3:6, 0:3]
            abs_diff = abs(res_beta - ref_beta)
            print(idxf, frequency)
            print(res_beta)
            print(abs_diff)
            assert (abs_diff < thresh).all()

    # from ecd import ECD
    # ecd = ECD(pyscfmol, C, E, occupations, do_dipvel=True, do_tda=False)
    # ecd.run()
    # ecd.form_results()
    # ord_solver.form_operators()
    # ord_solver.run()
    # ord_solver.form_results()
    # from constants import esuecd
    # prefac = -(2 / 3) / esuecd
    # for idxf, frequency in enumerate(frequencies):
    #     print(sum(prefac * ecd.rotational_strengths_diplen / ((frequency ** 2) * (ecd.solver.eigvals.real ** 2))))

    return