Пример #1
0
    def read(self, filename):

        self.lrtddft = LrTDDFT(filename + '/' + filename + '.lr.dat.gz')
        self.atoms, self.calculator = restart(
            filename + '/' + filename, communicator=self.world)
        E0 = self.calculator.get_potential_energy()

        f = open(filename + '/' + filename + '.exst', 'r')
        f.readline()
        self.d = f.readline().replace('\n', '').split()[1]
        indextype = f.readline().replace('\n', '').split()[1]
        if indextype == 'UnconstraintIndex':
            iex = int(f.readline().replace('\n', '').split()[1])
            self.index = UnconstraintIndex(iex)
        else:
            direction = f.readline().replace('\n', '').split()[1]
            if direction in [str(0), str(1), str(2)]:
                direction = int(direction)
            else:
                direction = None

            val = f.readline().replace('\n', '').split()
            if indextype == 'MinimalOSIndex':

                self.index = MinimalOSIndex(float(val[1]), direction)
            else:
                emin = float(val[2])
                emax = float(val[3].replace(']', ''))
                self.index = MaximalOSIndex([emin, emax], direction)

        index = self.index.apply(self.lrtddft)
        self.results['energy'] = E0 + self.lrtddft[index].energy * Hartree
        self.lrtddft.set_calculator(self.calculator)
Пример #2
0
def make_force_sets_and_excitations(cachepath, disp_filenames, phonon, atoms,
                                    ex_kw):
    if os.path.exists(cachepath):
        parprint(f'Found existing {cachepath}')
        return np.load(cachepath)
    world.barrier()
    parprint(
        f'Computing force sets and polarizability data at displacements... ({cachepath})'
    )

    eq_atoms = atoms.copy()

    def iter_displacement_files():
        eq_force_filename = disp_filenames['force']['eq']
        eq_ex_filename = disp_filenames['ex']['eq']
        yield 'eq', eq_force_filename, eq_ex_filename, eq_atoms

        disp_phonopy_sites, disp_carts = get_phonopy_displacements(phonon)
        for i, disp_atoms in enumerate(
                iter_displaced_structures(atoms, disp_phonopy_sites,
                                          disp_carts)):
            force_filename = disp_filenames['force']['disp'].format(i)
            ex_filename = disp_filenames['ex']['disp'].format(i)
            yield 'disp', force_filename, ex_filename, disp_atoms

    # Make files for one displacement at a time
    for disp_kind, force_filename, ex_filename, disp_atoms in iter_displacement_files(
    ):
        if os.path.exists(ex_filename):
            continue
        world.barrier()
        atoms.set_positions(disp_atoms.get_positions())

        disp_forces = atoms.get_forces()
        ex = LrTDDFT(atoms.calc, **ex_kw)
        if disp_kind == 'eq':
            # For inspecting the impact of differences in the calculator
            # between ionic relaxation and raman computation.
            parprint('Max equilibrium force during raman:',
                     np.absolute(disp_forces).max())
        if world.rank == 0:
            np.save(force_filename, disp_forces)
        ex.write(ex_filename)

    # combine force sets into one file
    force_sets = np.array([
        np.load(disp_filenames['force']['disp'].format(i))
        for i in range(len(phonon.get_displacements()))
    ])
    np.save(cachepath, force_sets)
    for i in range(len(phonon.get_displacements())):
        os.unlink(disp_filenames['force']['disp'].format(i))
    return force_sets
Пример #3
0
def expand_raman_by_symmetry(cachepath, phonon, disp_filenames,
                             get_polarizability, ex_kw,
                             subtract_equilibrium_polarizability):
    if os.path.exists(cachepath):
        parprint(f'Found existing {cachepath}')
        return np.load(cachepath)
    world.barrier()
    parprint(f'Expanding raman data by symmetry... ({cachepath})')

    disp_phonopy_sites, disp_carts = get_phonopy_displacements(phonon)

    prim_symmetry = phonon.primitive_symmetry.get_symmetry_operations()
    lattice = phonon.primitive.get_cell()[...]
    carts = phonon.primitive.get_positions()

    oper_frac_rots = prim_symmetry['rotations']
    oper_frac_trans = prim_symmetry['translations']
    oper_cart_rots = np.array(
        [np.linalg.inv(lattice).T @ R @ lattice.T for R in oper_frac_rots])
    oper_cart_trans = oper_frac_trans @ lattice

    oper_deperms = []
    for cart_rot, cart_trans in zip(oper_cart_rots, oper_cart_trans):
        carts = phonon.primitive.get_positions()
        transformed_carts = carts @ cart_rot.T + cart_trans
        oper_deperms.append(get_deperm(carts, transformed_carts, lattice))
    oper_deperms = np.array(oper_deperms)

    disp_tensors = np.array([
        get_polarizability(
            LrTDDFT.read(disp_filenames['ex']['disp'].format(i), **ex_kw))
        for i in range(len(disp_phonopy_sites))
    ])
    if subtract_equilibrium_polarizability:
        disp_tensors -= get_polarizability(
            LrTDDFT.read(disp_filenames['ex']['eq'], **ex_kw))

    pol_derivs = symmetry.expand_derivs_by_symmetry(
        disp_phonopy_sites,
        disp_carts,
        disp_tensors,
        symmetry.Tensor2Callbacks(),
        oper_cart_rots,
        oper_deperms,
    )
    pol_derivs = np.array(
        pol_derivs.tolist())  # (n,3) dtype=object --> (n,3,3,3) dtype=complex

    np.save(cachepath, pol_derivs)
    return pol_derivs
Пример #4
0
def show(c2):
    c2.calculate(H2)
    ov = Overlap(c1).pseudo(c2)
    parprint('wave function overlap (pseudo):\n', ov)
    ov = Overlap(c1).full(c2)
    parprint('wave function overlap (full):\n', ov)
    lr2 = LrTDDFT(c2)
    ovkss = lr1.kss.overlap(ov[0], lr2.kss)
    parprint('KSSingles overlap:\n', ovkss)
    ovlr = lr1.overlap(ov[0], lr2)
    parprint('LrTDDFT overlap:\n', ovlr)
Пример #5
0
#load=True
if not io_only:
    R=0.7 # approx. experimental bond length
    a = 3.0
    c = 4.0
    H2 = Atoms([Atom('H', (a / 2, a / 2, (c - R) / 2)),
                Atom('H', (a / 2, a / 2, (c + R) / 2))],
               cell=(a, a, c))
    calc = GPAW(xc='PBE', nbands=3, spinpol=False, txt=txt)
    H2.set_calculator(calc)
    H2.get_potential_energy()

    xc='LDA'

    # without spin
    lr = LrTDDFT(calc, xc=xc)
    lr.diagonalize()
    t1 = lr[0]

    # course grids
    for finegrid in [1,0]:
        lr = LrTDDFT(calc, xc=xc, finegrid=finegrid)
        lr.diagonalize()
        t3 = lr[0]
        print 'finegrid, t1, t3=', finegrid, t1 ,t3
        equal(t1.get_energy(), t3.get_energy(), 5.e-4)

    # with spin
    
    lr_vspin = LrTDDFT(calc, xc=xc, nspins=2)
    singlet, triplet = lr_vspin.singlets_triplets()
Пример #6
0
class ExcitedState(GPAW):

    def __init__(self, lrtddft=None, index=0, d=0.001, txt=None,
                 parallel=0, communicator=None, name=None, restart=None):
        """ExcitedState object.
        parallel: Can be used to parallelize the numerical force calculation
        over images.
        """

        self.timer = Timer()
        self.atoms = None
        if isinstance(index, int):
            self.index = UnconstraintIndex(index)
        else:
            self.index = index

        self.results = {}
        self.results['forces'] = None
        self.results['energy'] = None
        if communicator is None:
            try:
                communicator = lrtddft.calculator.wfs.world
            except:
                communicator = mpi.world
        self.world = communicator

        if restart is not None:
            self.read(restart)
            if txt is None:
                self.txt = self.lrtddft.txt
            else:
                self.txt = convert_string_to_fd(txt, self.world)

        if lrtddft is not None:
            self.lrtddft = lrtddft
            self.calculator = self.lrtddft.calculator
            self.atoms = self.calculator.atoms
            self.parameters = self.calculator.parameters
            if txt is None:
                self.txt = self.lrtddft.txt
            else:
                self.txt = convert_string_to_fd(txt, self.world)

        self.d = d
        self.parallel = parallel
        self.name = name

        self.log = GPAWLogger(self.world)
        self.log.fd = self.txt
        self.reader = None
        self.calculator.log.fd = self.txt
        self.log('#', self.__class__.__name__, __version__)
        self.log('#', self.index)
        if name:
            self.log('name=' + name)
        self.log('# Force displacement:', self.d)
        self.log

    def __del__(self):
        self.timer.write(self.log.fd)

    def set(self, **kwargs):
        self.calculator.set(**kwargs)

    def set_positions(self, atoms):
        """Update the positions of the atoms."""

        self.atoms = atoms.copy()
        self.results['forces'] = None
        self.results['energy'] = None

    def write(self, filename, mode=''):

        try:
            os.makedirs(filename)
        except OSError as exception:
            if exception.errno != errno.EEXIST:
                raise

        self.calculator.write(filename=filename + '/' + filename, mode=mode)
        self.lrtddft.write(filename=filename + '/' + filename + '.lr.dat.gz',
                           fh=None)

        f = open(filename + '/' + filename + '.exst', 'w')
        f.write('# ' + self.__class__.__name__ + __version__ + '\n')
        f.write('Displacement: {0}'.format(self.d) + '\n')
        f.write('Index: ' + self.index.__class__.__name__ + '\n')
        for k, v in self.index.__dict__.items():
            f.write('{0}, {1}'.format(k, v) + '\n')
        f.close()

        mpi.world.barrier()

    def read(self, filename):

        self.lrtddft = LrTDDFT(filename + '/' + filename + '.lr.dat.gz')
        self.atoms, self.calculator = restart(
            filename + '/' + filename, communicator=self.world)
        E0 = self.calculator.get_potential_energy()

        f = open(filename + '/' + filename + '.exst', 'r')
        f.readline()
        self.d = f.readline().replace('\n', '').split()[1]
        indextype = f.readline().replace('\n', '').split()[1]
        if indextype == 'UnconstraintIndex':
            iex = int(f.readline().replace('\n', '').split()[1])
            self.index = UnconstraintIndex(iex)
        else:
            direction = f.readline().replace('\n', '').split()[1]
            if direction in [str(0), str(1), str(2)]:
                direction = int(direction)
            else:
                direction = None

            val = f.readline().replace('\n', '').split()
            if indextype == 'MinimalOSIndex':

                self.index = MinimalOSIndex(float(val[1]), direction)
            else:
                emin = float(val[2])
                emax = float(val[3].replace(']', ''))
                self.index = MaximalOSIndex([emin, emax], direction)

        index = self.index.apply(self.lrtddft)
        self.results['energy'] = E0 + self.lrtddft[index].energy * Hartree
        self.lrtddft.set_calculator(self.calculator)

    def calculation_required(self, atoms, quantities):
        if len(quantities) == 0:
            return False

        if self.atoms is None:
            return True

        elif (len(atoms) != len(self.atoms) or
              (atoms.get_atomic_numbers() !=
               self.atoms.get_atomic_numbers()).any() or
              (atoms.get_initial_magnetic_moments() !=
               self.atoms.get_initial_magnetic_moments()).any() or
              (atoms.get_cell() != self.atoms.get_cell()).any() or
              (atoms.get_pbc() != self.atoms.get_pbc()).any()):
            return True
        elif (atoms.get_positions() !=
              self.atoms.get_positions()).any():
            return True

        for quantity in ['energy', 'forces']:
            if quantity in quantities:
                quantities.remove(quantity)
                if self.results[quantity] is None:
                    return True
        return len(quantities) > 0

    def check_state(self, atoms, tol=1e-15):
        system_changes = GPAW.check_state(self.calculator, atoms, tol)
        return system_changes

    def get_potential_energy(self, atoms=None, force_consistent=None):
        """Evaluate potential energy for the given excitation."""

        if atoms is None:
            atoms = self.atoms

        if self.calculation_required(atoms, ['energy']):
            self.results['energy'] = self.calculate(atoms)

        return self.results['energy']

    def calculate(self, atoms):
        """Evaluate your energy if needed."""
        self.set_positions(atoms)

        self.calculator.calculate(atoms)
        E0 = self.calculator.get_potential_energy()
        atoms.set_calculator(self)

        if hasattr(self, 'density'):
            del(self.density)
        self.lrtddft.forced_update()
        self.lrtddft.diagonalize()

        index = self.index.apply(self.lrtddft)

        energy = E0 + self.lrtddft[index].energy * Hartree

        self.log('--------------------------')
        self.log('Excited state')
        self.log(self.index)
        self.log('Energy:   {0}'.format(energy))
        self.log()

        return energy

    def get_forces(self, atoms=None, save=False):
        """Get finite-difference forces
        If save = True, restartfiles for every displacement are given
        """
        if atoms is None:
            atoms = self.atoms

        if self.calculation_required(atoms, ['forces']):
            atoms.set_calculator(self)

            # do the ground state calculation to set all
            # ranks to the same density to start with
            E0 = self.calculate(atoms)

            finite = FiniteDifference(
                atoms=atoms,
                propertyfunction=atoms.get_potential_energy,
                save=save,
                name="excited_state", ending='.gpw',
                d=self.d, parallel=self.parallel)
            F_av = finite.run()

            self.set_positions(atoms)
            self.results['energy'] = E0
            self.results['forces'] = F_av
            if self.txt:
                self.log('Excited state forces in eV/Ang:')
                symbols = self.atoms.get_chemical_symbols()
                for a, symbol in enumerate(symbols):
                    self.log(('%3d %-2s %10.5f %10.5f %10.5f' %
                              ((a, symbol) +
                               tuple(self.results['forces'][a]))))
        return self.results['forces']

    def forces_indexn(self, index):
        """ If restartfiles are created from the force calculation,
        this function allows the calculation of forces for every
        excited state index.
        """
        atoms = self.atoms

        def reforce(self, name):
            excalc = ExcitedState(index=index, restart=name)
            return excalc.get_potential_energy()

        fd = FiniteDifference(
            atoms=atoms, save=True,
            propertyfunction=self.atoms.get_potential_energy,
            name="excited_state", ending='.gpw',
            d=self.d, parallel=0)
        atoms.set_calculator(self)

        return fd.restart(reforce)

    def get_stress(self, atoms):
        """Return the stress for the current state of the Atoms."""
        raise NotImplementedError

    def initialize_density(self, method='dipole'):
        if hasattr(self, 'density') and self.density.method == method:
            return

        gsdensity = self.calculator.density
        lr = self.lrtddft
        self.density = ExcitedStateDensity(
            gsdensity.gd, gsdensity.finegd, lr.kss.npspins,
            gsdensity.charge,
            method=method, redistributor=gsdensity.redistributor)
        index = self.index.apply(self.lrtddft)
        self.density.initialize(self.lrtddft, index)
        self.density.update(self.calculator.wfs)

    def get_pseudo_density(self, **kwargs):
        """Return pseudo-density array."""
        method = kwargs.pop('method', 'dipole')
        self.initialize_density(method)
        return GPAW.get_pseudo_density(self, **kwargs)

    def get_all_electron_density(self, **kwargs):
        """Return all electron density array."""
        method = kwargs.pop('method', 'dipole')
        self.initialize_density(method)
        return GPAW.get_all_electron_density(self, **kwargs)
Пример #7
0
from gpaw import GPAW
from gpaw.lrtddft import LrTDDFT

c = GPAW('Be_gs_8bands.gpw')

istart = 0  # band index of the first occ. band to consider
jend = 8  # band index of the last unocc. band to consider
lr = LrTDDFT(c, xc='LDA', istart=istart, jend=jend,
             nspins=2)  # force the calculation of triplet excitations also
lr.write('lr.dat.gz')
from ase import Atoms
from gpaw import GPAW
from gpaw.lrtddft import LrTDDFT

# Na2 cluster
atoms = Atoms(symbols='Na2', 
              positions=[(0, 0, 0), (3.0, 0, 0)],
              pbc=False)
atoms.center(vacuum=6.0)

# Standard ground state calculation with empty states
calc = GPAW(nbands=100, h=0.4, setups={'Na': '1'})
atoms.set_calculator(calc)
energy = atoms.get_potential_energy()

calc.set(convergence={'bands' : 90}, 
         fixdensity=True,
         eigensolver='cg')
calc.calculate()

calc.write('na2_gs_casida.gpw', mode='all')

# Standard Casida calculation
calc = GPAW('na2_gs_casida.gpw')
istart = 0
jend = 90
lr = LrTDDFT(calc, xc='LDA', istart=istart, jend=jend)
lr.diagonalize()
lr.write('na2_lr.dat.gz')
Пример #9
0
out = 'dospes.dat'
pes = DOSPES(calc, calc_plus, shift=True)
pes.save_folded_pes(filename=out, folding=None)
pes.save_folded_pes(filename=None, folding=None)

# check for correct shift
VDE = calc_plus.get_potential_energy() - calc.get_potential_energy()
BE_HOMO = 1.e23
be_n, f_n = pes.get_energies_and_weights()
for be, f in zip(be_n, f_n):
    if f > 0.1 and be < BE_HOMO:
        BE_HOMO = be
equal(BE_HOMO, VDE)

lr = LrTDDFT(calc_plus, xc=xc)

out = 'lrpes.dat'
pes = TDDFTPES(calc, lr)
pes.save_folded_pes(filename=out, folding='Gauss')
pes.save_folded_pes(filename=None, folding=None)

energy_tolerance = 0.0001
niter_tolerance = 1
equal(e_H2, -3.90059, energy_tolerance)
equal(e_H2_plus, 10.5659703, energy_tolerance)

# io
out = 'lrpes.dat.gz'
lr.write(out)
lr = LrTDDFT(out)
Пример #10
0
box = 2
nbands = 4
txt = '-'
txt = None
np.set_printoptions(precision=3, suppress=True)

H2 = Cluster(molecule('H2'))
H2.minimal_box(box, h)

c1 = GPAW(h=h,
          txt=txt,
          eigensolver='dav',
          nbands=nbands,
          convergence={'eigenstates': nbands})
c1.calculate(H2)
lr1 = LrTDDFT(c1)

parprint('sanity --------')
ov = Overlap(c1).pseudo(c1)
parprint('pseudo(normalized):\n', ov)
ov = Overlap(c1).pseudo(c1, False)
parprint('pseudo(not normalized):\n', ov)
ov = Overlap(c1).full(c1)
parprint('full:\n', ov)
equal(ov[0], np.eye(ov[0].shape[0], dtype=ov.dtype), 1e-10)


def show(c2):
    c2.calculate(H2)
    ov = Overlap(c1).pseudo(c2)
    parprint('wave function overlap (pseudo):\n', ov)
Пример #11
0
from gpaw import GPAW
from gpaw.lrtddft import LrTDDFT

c = GPAW('Be_gs_8bands.gpw')

dE = 10  # maximal Kohn-Sham transition energy to consider in eV
lr = LrTDDFT(c, xc='LDA', energy_range=dE)
lr.write('lr_dE.dat.gz')
Пример #12
0
# folder function

for name in ['Gauss', 'Lorentz']:
    folder = Folder(width, name)

    x = [0, 2]
    y = [[2, 0, 1], [1, 1, 1]]

    xl, yl = folder.fold(x, y, dx=.7)

    # check first value
    if name == 'Lorentz':
        func = Lorentz(width)
    else:
        func = Gauss(width)
    yy = np.dot(np.array(y)[:, 0], func.get(xl[0] - np.array(x)))
    equal(yl[0, 0], yy, 1.e-15)

# write spectrum

from gpaw.lrtddft import LrTDDFT
from gpaw.lrtddft.spectrum import spectrum

fname = 'lr.dat.gz'
if os.path.exists(fname):
    lr = LrTDDFT(fname)
    lr.diagonalize()
    spectrum(lr, 'spectrum.dat')

Пример #13
0
# External imports
import helper as h

from gpaw import GPAW
from gpaw.lrtddft import LrTDDFT

# Retrieve the calculator from task 1
lr = LrTDDFT('../task1/TDDFT_Task1.dat')

# Dump the results from the calculation to file
h.dump_data(lr, fpath='dumpTask1.npz')

# Also generate the discrete spectrum from GPAW
h.discrete_spectrum(lr, 'GPAW_discrete.dat')
Пример #14
0
    calc = GPAW(xc='PBE', nbands=2, spinpol=False, txt=txt)
    H2.set_calculator(calc)
    H2.get_potential_energy()
##    calc.write('H2.gpw', 'all')
else:
    calc = GPAW('H2.gpw', txt=txt)
#calc.initialize_wave_functions()

#-----------------------------------------------------------
# DFT only

xc='LDA'

# no spin

lr = LrTDDFT(calc, xc=xc)
lr.diagonalize()

lr_ApmB = LrTDDFT(calc, xc=xc, force_ApmB=True)
lr_ApmB.diagonalize()
print 'lr=', lr
print 'ApmB=', lr_ApmB
equal(lr[0].get_energy(), lr_ApmB[0].get_energy(), 5.e-10)

# with spin
print '------ with spin'

if not load:
    c_spin = GPAW(xc='PBE', nbands=2, 
                  spinpol=True, parallel={'domain': mpi.world.size},
                  txt=txt)
box = 5.     # box dimension
h = 0.25     # grid spacing
width = 0.01 # Fermi width
nbands = 6   # bands in GS calculation
nconv = 4    # bands in GS calculation to converge
R = 2.99     # starting distance
iex = 1      # excited state index
d = 0.01     # step for numerical force evaluation
exc = 'LDA'  # xc for the linear response TDDFT kernel

s = Cluster([Atom('Na'), Atom('Na', [0, 0, R])])
s.minimal_box(box, h=h)

c = GPAW(h=h, nbands=nbands, eigensolver='cg',
         occupations=FermiDirac(width=width),
         setups={'Na': '1'},
         convergence={'bands':nconv})
c.calculate(s)
lr = LrTDDFT(c, xc=exc, eps=0.1, jend=nconv-1)

ex = ExcitedState(lr, iex, d=d)
s.set_calculator(ex)

ftraj='relax_ex' + str(iex)
ftraj += '_box' + str(box) + '_h' + str(h)
ftraj += '_d' + str(d) + '.traj'
traj = io.PickleTrajectory(ftraj, 'w', s)
dyn = optimize.FIRE(s)
dyn.attach(traj.write)
dyn.run(fmax=0.05)
Пример #16
0
from gpaw import GPAW
from gpaw.cluster import Cluster
from gpaw.analyse.overlap import Overlap
import gpaw.solvation as solv
from gpaw.lrtddft import LrTDDFT
from gpaw.poisson import PoissonSolver
"""Check whether LrTDDFT in solvation works"""

h = 0.4
box = 2
nbands = 2
txt = '-'
txt = None

H2 = Cluster(molecule('H2'))
H2.minimal_box(box, h)

c1 = GPAW(h=h, txt=None, nbands=nbands)
c1.calculate(H2)

c2 = solv.SolvationGPAW(h=h,
                        txt=None,
                        nbands=nbands + 1,
                        **solv.get_HW14_water_kwargs())
c2.calculate(H2)
for poiss in [None, PoissonSolver(nn=c2.hamiltonian.poisson.nn)]:
    lr = LrTDDFT(c2, poisson=poiss)
    print(lr)
print(Overlap(c1).pseudo(c2))
# Built-in packages
import time

# GPAW
from gpaw import GPAW
from gpaw.lrtddft import LrTDDFT
from gpaw.lrtddft import photoabsorption_spectrum

print(
    f'------------   Extracting shortened photoabsorption spectrum   ------------'
)

start = time.time()

# Import LrTDDFT results from Task 1
lr = LrTDDFT('../task1/TDDFT_Task1.dat')

lr.diagonalize(energy_range=4)  # Only include up to 4 eV

# Generate spectrum and save it
wd = 0.06
photoabsorption_spectrum(lr, f'spectrum_w{wd}.dat', width=wd)

# Extract all information about all transitions
print('** LrTDDFT.analyse() output **')
lr.analyse()
print('*******************************')

end = time.time()
print('-------- Photoabsorption spectrum extracted in: ' +
      f'{(end-start):.2f} s --------'.rjust(34))
Пример #18
0
H2.set_calculator(calc)
e_H2 = H2.get_potential_energy()
niter_H2 = calc.get_number_of_iterations()

calc_plus = GPAW(gpts=(12, 12, 12),
                 xc=xc,
                 nbands=2,
                 parallel={'domain': mpi.world.size},
                 spinpol=True,
                 txt=txt)
calc_plus.set(charge=+1)
H2_plus.set_calculator(calc_plus)
e_H2_plus = H2_plus.get_potential_energy()
niter_H2_plus = calc.get_number_of_iterations()

lr = LrTDDFT(calc_plus, xc=xc)

pes = DOSPES(calc, calc_plus)
pes.save_folded_pes(filename=txt, folding=None)
pes.save_folded_pes(filename=None, folding=None)

pes = TDDFTPES(calc, lr)
pes.save_folded_pes(filename=txt, folding='Gauss')
pes.save_folded_pes(filename=None, folding=None)

energy_tolerance = 0.000008
niter_tolerance = 0
equal(e_H2, -3.90059, energy_tolerance)
equal(niter_H2, 15, niter_tolerance)
equal(e_H2_plus, 10.5659703, energy_tolerance)
equal(niter_H2_plus, 15, niter_tolerance)
Пример #19
0
from ase import Atoms
from gpaw import GPAW
from gpaw.lrtddft import LrTDDFT

# Na2 cluster
atoms = Atoms(symbols='Na2', positions=[(0, 0, 0), (3.0, 0, 0)], pbc=False)
atoms.center(vacuum=6.0)

# Standard ground state calculation with empty states
calc = GPAW(nbands=100, h=0.4, setups={'Na': '1'})
atoms.set_calculator(calc)
energy = atoms.get_potential_energy()

calc.set(convergence={'bands': 90}, fixdensity=True, eigensolver='cg')
atoms.get_potential_energy()

calc.write('na2_gs_casida.gpw', mode='all')

# Standard Casida calculation
calc = GPAW('na2_gs_casida.gpw')
istart = 0
jend = 90
lr = LrTDDFT(calc, xc='LDA', istart=istart, jend=jend)
lr.diagonalize()
lr.write('na2_lr.dat.gz')
Пример #20
0
#load=True
if not io_only:
    R=0.7 # approx. experimental bond length
    a = 3.0
    c = 4.0
    H2 = Atoms([Atom('H', (a / 2, a / 2, (c - R) / 2)),
                Atom('H', (a / 2, a / 2, (c + R) / 2))],
               cell=(a, a, c))
    calc = GPAW(xc='PBE', nbands=3, spinpol=False, txt=txt)
    H2.set_calculator(calc)
    H2.get_potential_energy()

    xc='LDA'

    # without spin
    lr = LrTDDFT(calc, xc=xc)
    lr.diagonalize()
    t1 = lr[0]
    lr_calc = lr
    ex = ExcitedState(lr, 0)
    den = ex.get_pseudo_density() * Bohr**3

    # course grids
    for finegrid in [1,0]:
        lr = LrTDDFT(calc, xc=xc, finegrid=finegrid)
        lr.diagonalize()
        t3 = lr[0]
        parprint('finegrid, t1, t3=', finegrid, t1 ,t3)
        equal(t1.get_energy(), t3.get_energy(), 5.e-4)

    # with spin
Пример #21
0
from gpaw import GPAW
from gpaw.lrtddft import LrTDDFT

c = GPAW('Be_gs_8bands.gpw')

istart=0 # band index of the first occ. band to consider
jend=8  # band index of the last unocc. band to consider
lr = LrTDDFT(c, xc='LDA', istart=istart, jend=jend,
             nspins=2) # force the calculation of triplet excitations also
lr.write('lr.dat.gz')
Пример #22
0
out = 'dospes.dat'
pes = DOSPES(calc, calc_plus, shift=True)
pes.save_folded_pes(filename=out, folding=None)
pes.save_folded_pes(filename=None, folding=None)

# check for correct shift
VDE = calc_plus.get_potential_energy() - calc.get_potential_energy()
BE_HOMO = 1.e23
be_n, f_n = pes.get_energies_and_weights()
for be, f in zip(be_n, f_n):
    if f > 0.1 and be < BE_HOMO:
        BE_HOMO = be
equal(BE_HOMO, VDE)

lr = LrTDDFT(calc_plus, xc=xc)

out = 'lrpes.dat'
pes = TDDFTPES(calc, lr)
pes.save_folded_pes(filename=out, folding='Gauss')
pes.save_folded_pes(filename=None, folding=None)

energy_tolerance = 0.0001
niter_tolerance = 1
equal(e_H2, -3.90059, energy_tolerance)
equal(e_H2_plus, 10.5659703, energy_tolerance)

# io
out = 'lrpes.dat.gz'
lr.write(out)
lr = LrTDDFT(out)
Пример #23
0
from gpaw import GPAW
from ase import Atoms
from gpaw.lrtddft import LrTDDFT

molecule = Atoms('Na2', positions=((0.0, 0.0, 0.0), (3.12, 0.0, 0.0)))

molecule.center(vacuum=6.0)

calc = GPAW(xc='PBE')

molecule.set_calculator(calc)

molecule.get_potential_energy()

lr = LrTDDFT(calc, xc='LDA', istart=0, jend=10, nspins=2)
lr.write('Omega_Na2.gz')
Пример #24
0
    calc = GPAW(xc='PBE', nbands=2, spinpol=False, txt=txt)
    H2.set_calculator(calc)
    H2.get_potential_energy()
##    calc.write('H2.gpw', 'all')
else:
    calc = GPAW('H2.gpw', txt=txt)
#calc.initialize_wave_functions()

#-----------------------------------------------------------
# DFT only

xc = 'LDA'

# no spin

lr = LrTDDFT(calc, xc=xc)
lr.diagonalize()

lr_ApmB = LrTDDFT(calc, xc=xc, force_ApmB=True)
lr_ApmB.diagonalize()
parprint('lr=', lr)
parprint('ApmB=', lr_ApmB)
equal(lr[0].get_energy(), lr_ApmB[0].get_energy(), 5.e-10)

# with spin
parprint('------ with spin')

if not load:
    c_spin = GPAW(xc='PBE',
                  nbands=2,
                  spinpol=True,
Пример #25
0
from gpaw import GPAW
from gpaw.lrtddft import LrTDDFT

c = GPAW('Be_gs_8bands.gpw')

dE = 10 # maximal Kohn-Sham transition energy to consider in eV
lr = LrTDDFT(c, xc='LDA', energy_range=dE)
lr.write('lr_dE.dat.gz')
Пример #26
0
txt = '-'
txt = '/dev/null'

R = 0.7  # approx. experimental bond length
a = 3.0
c = 4.0
H2 = Atoms([
    Atom('H', (a / 2, a / 2, (c - R) / 2)),
    Atom('H', (a / 2, a / 2, (c + R) / 2))
],
           cell=(a, a, c))
calc = GPAW(xc='PBE', h=0.25, nbands=3, spinpol=False, txt=txt)
H2.set_calculator(calc)

xc = 'LDA'
lr = LrTDDFT(calc, xc=xc)

# excited state with forces
accuracy = 0.015
exst = ExcitedState(lr, 0, d=0.01, parallel=2, txt=sys.stdout)

t0 = time.time()
parprint("########### first call to forces --> calculate")
forces = exst.get_forces(H2)
parprint("time used:", time.time() - t0)
for c in range(2):
    equal(forces[0, c], 0.0, accuracy)
    equal(forces[1, c], 0.0, accuracy)
equal(forces[0, 2] + forces[1, 2], 0.0, accuracy)

parprint("########### second call to potential energy --> just return")
Пример #27
0
c = 5.0
H2 = Atoms([
    Atom('H', (a / 2, a / 2, (c - R) / 2)),
    Atom('H', (a / 2, a / 2, (c + R) / 2))
],
           cell=(a, a, c))

calc = GPAW(xc=xc, nbands=2, spinpol=False, eigensolver='rmm-diis', txt=txt)
H2.set_calculator(calc)
H2.get_potential_energy()
calc.write('H2saved_wfs.gpw', 'all')
calc.write('H2saved.gpw')
wfs_error = calc.wfs.eigensolver.error

#print "-> starting directly after a gs calculation"
lr = LrTDDFT(calc, txt='-')
lr.diagonalize()

#print "-> reading gs with wfs"
gs = GPAW('H2saved_wfs.gpw', txt=txt)

# check that the wfs error is read correctly,
# but take rounding errors into account
assert (abs(calc.wfs.eigensolver.error / gs.wfs.eigensolver.error - 1) < 1e-8)
lr1 = LrTDDFT(gs, xc=xc, txt='-')
lr1.diagonalize()
# check the oscillator strrength
assert (abs(lr1[0].get_oscillator_strength()[0] /
            lr[0].get_oscillator_strength()[0] - 1) < 1e-10)

#print "-> reading gs without wfs"
Пример #28
0
              mode='RPA',
              coupling=True,
              q=np.array([0,0,0.0001]),
              optical_limit=True,
              ecut=50.,
              nbands=8)
    bse.initialize()
    H_SS = bse.calculate()
    bse.diagonalize(H_SS)
    
    w = np.real(bse.w_S) * Hartree
    print np.shape(w)
    energies = np.sort(w)[len(w)/2:]
    print 'BSE:', energies

if casida:
    from gpaw.lrtddft import LrTDDFT
    from gpaw.lrtddft import photoabsorption_spectrum

    calc = GPAW('Na2.gpw',txt=None)

    lr = LrTDDFT(calc, xc=None, istart=0, jend=7, nspins=1) 
    lr.diagonalize()
    photoabsorption_spectrum(lr, 'Na2_spectrum.dat', width=0.05)   

    energies_lrtddft = lr.get_energies() * Hartree
    print 'lrTDDFT:', energies_lrtddft
    
if compare:
    assert (np.abs(energies - energies_lrtddft)).max() < 3*1e-3
Пример #29
0
                h=0.3,
                occupations=FermiDirac(width=0.0, fixmagmom=True))


calc = get_paw()
calc.set(txt='H2O_LCY_PBE_083.log')
calc_plus = get_paw()
calc_plus.set(txt='H2O_plus_LCY_PBE_083.log', charge=1)

h2o.set_calculator(calc)
e_h2o = h2o.get_potential_energy()
h2o_plus.set_calculator(calc_plus)
e_h2o_plus = h2o_plus.get_potential_energy()
e_ion = e_h2o_plus - e_h2o

print(e_ion, 12.62)
equal(e_ion, 12.62, 0.1)
lr = LrTDDFT(calc_plus, txt='LCY_TDDFT_H2O.log', jend=4)
equal(lr.xc.omega, 0.83)
lr.write('LCY_TDDFT_H2O.ex.gz')
# reading is problematic with EXX on more than one core
if world.rank == 0:
    lr2 = LrTDDFT('LCY_TDDFT_H2O.ex.gz')
    lr2.diagonalize()
    equal(lr2.xc.omega, 0.83)

    for i, ip_i in enumerate([14.74, 18.51]):
        ion_i = lr2[i].get_energy() * Hartree + e_ion
        print(ion_i, ip_i)
        equal(ion_i, ip_i, 0.6)
Пример #30
0
from gpaw import restart
from gpaw.lrtddft import LrTDDFT, photoabsorption_spectrum

atoms, calc = restart('na2_gs_unocc.gpw')

# Calculate the omega matrix
lr = LrTDDFT(calc, xc='LDA', jend=5) # Use only 5 unoccupied states

# Save the omega matrix
lr.write('Omega_Na2.gz')

# Diagonalize the matrix
lr.diagonalize()

# Analyse 5 lowest excitations
lr.analyse(range(5))
photoabsorption_spectrum(lr, 'Na2_spectrum.dat', e_min=0.0, e_max=10)
Пример #31
0
if setup_paths[0] != '.':
    setup_paths.insert(0, '.')

gen('Mg', xcname='PBE', scalarrel=True, exx=True, yukawa_gamma=0.38)

c = {'energy': 0.05, 'eigenstates': 3, 'density': 3}
na2 = Cluster(Atoms('Mg', positions=[[0, 0, 0]]))
na2.minimal_box(2.5, h=h)
calc = GPAW(txt='mg_ivo.txt',
            xc='LCY-PBE:omega=0.38:excitation=singlet',
            eigensolver=RMMDIIS(),
            h=h,
            occupations=FermiDirac(width=0.0),
            spinpol=False,
            convergence=c)
na2.set_calculator(calc)
na2.get_potential_energy()
(eps_homo, eps_lumo) = calc.get_homo_lumo()
e_ex = eps_lumo - eps_homo
equal(e_singlet, e_ex, 0.15)
calc.write('mg.gpw')
c2 = GPAW('mg.gpw')
assert c2.hamiltonian.xc.excitation == 'singlet'
lr = LrTDDFT(calc, txt='LCY_TDDFT_Mg.log', istart=4, jend=5, nspins=2)
lr.write('LCY_TDDFT_Mg.ex.gz')
if world.rank == 0:
    lr2 = LrTDDFT('LCY_TDDFT_Mg.ex.gz')
    lr2.diagonalize()
    ex_lr = lr2[1].get_energy() * Hartree
    equal(e_singlet_lr, ex_lr, 0.15)
Пример #32
0
from gpaw import GPAW
from gpaw.lrtddft import LrTDDFT, photoabsorption_spectrum
from gpaw.inducedfield.inducedfield_lrtddft import LrTDDFTInducedField

# Load LrTDDFT object
lr = LrTDDFT('na2_lr.dat.gz')

# Calculate photoabsorption spectrum as usual
folding = 'Gauss'
width = 0.1
e_min = 0.0
e_max = 4.0
photoabsorption_spectrum(lr,
                         'na2_casida_spectrum.dat',
                         folding=folding,
                         width=width,
                         e_min=e_min,
                         e_max=e_max,
                         delta_e=1e-2)

# Load GPAW object
calc = GPAW('na2_gs_casida.gpw')

# Calculate induced field
frequencies = [1.0, 2.08]  # Frequencies of interest in eV
folding = 'Gauss'  # Folding function
width = 0.1  # Line width for folding in eV
kickdir = 0  # Kick field direction 0, 1, 2 for x, y, z
ind = LrTDDFTInducedField(paw=calc,
                          lr=lr,
                          frequencies=frequencies,
Пример #33
0
           parallel={'domain': mpi.size},
           xc='PBE', txt='CO-m.txt', spinpol=True)

m = atoms.copy()
m.set_initial_magnetic_moments([-1,1])
m.set_calculator(m_c)
m.get_potential_energy()

d_c = GPAW(gpts=N_c, nbands=16, mixer=MixerDif(0.1, 5, weight=100.0),
           convergence={'bands':10},
           parallel={'domain': mpi.size},
           xc='PBE', txt='CO-d.txt', spinpol=True)

d = atoms.copy()
d.set_initial_magnetic_moments([-1,1])
d_c.set(charge=1)
d.set_calculator(d_c)
d.get_potential_energy()

istart=0 # band index of the first occ. band to consider
jend=15  # band index of the last unocc. band to consider
d_lr = LrTDDFT(d_c, xc='PBE', nspins=2 , istart=istart, jend=jend)
d_lr.diagonalize()

pes = TDDFTPES(m_c, d_lr, d_c)
pes.save_folded_pes('CO-td.dat', folding=None)

pes = DOSPES(m_c, d_c)
pes.save_folded_pes('CO-dos.dat', folding=None)

Пример #34
0
    # selection using an energy range
    el = obj(calc, energy_range=8, txt=txt)
    if hasattr(obj, 'diagonalize'):
        el.diagonalize()
#    print "*************** obj, len(obj)", obj.__name__, len(el)
    assert len(el) == 4
    el = obj(calc, energy_range=11.5, txt=txt)
    #    print "*************** obj, len(obj)", obj.__name__, len(el)
    if hasattr(obj, 'diagonalize'):
        el.diagonalize()
    assert len(el) == 18
    if hasattr(obj, 'diagonalize'):
        el.diagonalize(energy_range=8)
        assert len(el) == 4

lr = LrTDDFT(calc, nspins=2)
lr.write('lrtddft3.dat.gz')
lr.diagonalize()

world.barrier()

# This is done to test if writing and reading again yields the same result
lr2 = LrTDDFT('lrtddft3.dat.gz')
lr2.diagonalize()

# Unfortunately not all of the lrtddft code is parallel
if rank == 0:
    Epeak = 19.5  # The peak we want to investigate (this is alone)
    Elist = np.asarray([lrsingle.get_energy() * Hartree for lrsingle in lr])
    n = np.argmin(np.abs(Elist - Epeak))  # Index of the peak
Пример #35
0
if setup_paths[0] != '.':
    setup_paths.insert(0, '.')

gen('Na', xcname='PBE', scalarrel=True, exx=True, yukawa_gamma=0.40)
gen('Cl', xcname='PBE', scalarrel=True, exx=True, yukawa_gamma=0.40)

c = {'energy': 0.005, 'eigenstates': 1e-2, 'density': 1e-2}
mol = Cluster(molecule('NaCl'))
mol.minimal_box(5.0, h=h)
calc = GPAW(txt='NaCl.txt',
            xc='LCY-PBE:omega=0.40:excitation=singlet',
            eigensolver=RMMDIIS(),
            h=h,
            occupations=FermiDirac(width=0.0),
            spinpol=False,
            convergence=c)
mol.set_calculator(calc)
mol.get_potential_energy()
(eps_homo, eps_lumo) = calc.get_homo_lumo()
e_ex = eps_lumo - eps_homo
equal(e_singlet, e_ex, 0.15)
calc.write('NaCl.gpw')

lr = LrTDDFT(calc, txt='LCY_TDDFT_NaCl.log', istart=6, jend=7, nspins=2)
lr.write('LCY_TDDFT_NaCl.ex.gz')
if world.rank == 0:
    lr2 = LrTDDFT('LCY_TDDFT_NaCl.ex.gz')
    lr2.diagonalize()
    ex_lr = lr2[1].get_energy() * Hartree
    equal(e_singlet_lr, e_singlet, 0.05)
Пример #36
0
from gpaw import restart
from gpaw.lrtddft import LrTDDFT, photoabsorption_spectrum

atoms, calc = restart('na2_gs_unocc.gpw')

# Calculate the omega matrix
lr = LrTDDFT(calc, xc='LDA', jend=5)
# Use only 5 unoccupied states

# Save the omega matrix
lr.write('Omega_Na2.gz')

# Diagonalize the matrix
lr.diagonalize()

# Analyse 5 lowest excitations
lr.analyse(range(5))
photoabsorption_spectrum(lr, 'Na2_spectrum.dat', e_min=0.0, e_max=10)
Пример #37
0
    calc.write('Na2.gpw','all')

if bse:
    
    bse = BSE('Na2.gpw',w=np.linspace(0,15,151),
              q=np.array([0,0,0.0001]),optical_limit=True,ecut=50.,
              nbands=8)
    bse.initialize()
    bse.calculate()
    
    w = np.real(bse.w_S) * Hartree
    energies = np.sort(w[:,np.nonzero(w>0)[0]])
    print energies

if casida:

    from gpaw.lrtddft import LrTDDFT
    from gpaw.lrtddft import photoabsorption_spectrum

    calc = GPAW('Na2.gpw',txt=None)

    lr = LrTDDFT(calc, xc=None, istart=0, jend=7, nspins=1) 
    lr.diagonalize()
    photoabsorption_spectrum(lr, 'Na2_spectrum.dat', width=0.05)   

    energies_lrtddft =  lr.get_energies() * Hartree
    print 'lrTDDFT:', energies_lrtddft
    
if compare:
    assert (np.abs(energies - energies_lrtddft)).max() < 3*1e-3
Пример #38
0
           parallel={'domain': mpi.size},
           xc='PBE', txt='CO-m.txt', spinpol=True)

m = atoms.copy()
m.set_initial_magnetic_moments([-1,1])
m.set_calculator(m_c)
m.get_potential_energy()

d_c = GPAW(gpts=N_c, nbands=16, mixer=MixerDif(0.1, 5, weight=100.0),
           convergence={'bands':10},
           parallel={'domain': mpi.size},
           xc='PBE', txt='CO-d.txt', spinpol=True)

d = atoms.copy()
d.set_initial_magnetic_moments([-1,1])
d_c.set(charge=1)
d.set_calculator(d_c)
d.get_potential_energy()

istart=0 # band index of the first occ. band to consider
jend=15  # band index of the last unocc. band to consider
d_lr = LrTDDFT(d_c, xc='PBE', nspins=2 , istart=istart, jend=jend)
d_lr.diagonalize()

pes = TDDFTPES(m_c, d_lr, d_c)
pes.save_folded_pes('CO-td.dat', folding=None)

pes = DOSPES(m_c, d_c, shift=True)
pes.save_folded_pes('CO-dos.dat', folding=None)

Пример #39
0
from gpaw.lrtddft import LrTDDFT, photoabsorption_spectrum
lr = LrTDDFT(filename='Omega_Na2.gz')
lr.diagonalize()
lr.write('excitations_Na2.gz')
lr = LrTDDFT(filename='excitations_Na2.gz')
photoabsorption_spectrum(lr, 'Na2_spectrum.dat', e_min=0.0, e_max=10)
Пример #40
0
    # selection using an energy range
    el = obj(calc, energy_range=8, txt=txt)
    if hasattr(obj, 'diagonalize'):
        el.diagonalize()
#    print "*************** obj, len(obj)", obj.__name__, len(el)
    assert len(el) == 4
    el = obj(calc, energy_range=11.5, txt=txt)
#    print "*************** obj, len(obj)", obj.__name__, len(el)
    if hasattr(obj, 'diagonalize'):
        el.diagonalize()
    assert len(el) == 18
    if hasattr(obj, 'diagonalize'):
        el.diagonalize(energy_range=8)
        assert len(el) == 4

lr = LrTDDFT(calc, nspins=2)
lr.write('lrtddft3.dat.gz')
lr.diagonalize()

world.barrier()

# This is done to test if writing and reading again yields the same result
lr2 = LrTDDFT('lrtddft3.dat.gz')
lr2.diagonalize()

# Unfortunately not all of the lrtddft code is parallel
if rank == 0:
    Epeak = 19.5# The peak we want to investigate (this is alone)
    Elist = np.asarray([lrsingle.get_energy() * Hartree for lrsingle in lr])
    n = np.argmin(np.abs(Elist - Epeak)) # Index of the peak
Пример #41
0
R = 0.7  # approx. experimental bond length
a = 4.0
c = 5.0
H2 = Atoms([Atom('H', (a / 2, a / 2, (c - R) / 2)),
            Atom('H', (a / 2, a / 2, (c + R) / 2))],
           cell=(a, a, c))

calc = GPAW(xc=xc, nbands=2, spinpol=False, eigensolver='rmm-diis', txt=txt)
H2.set_calculator(calc)
H2.get_potential_energy()
calc.write('H2saved_wfs.gpw', 'all')
calc.write('H2saved.gpw')
wfs_error = calc.wfs.eigensolver.error

#print "-> starting directly after a gs calculation"
lr = LrTDDFT(calc, txt='-')
lr.diagonalize()

#print "-> reading gs with wfs"
gs = GPAW('H2saved_wfs.gpw', txt=txt)

# check that the wfs error is read correctly, 
# but take rounding errors into account
assert( abs(calc.wfs.eigensolver.error/gs.wfs.eigensolver.error - 1) < 1e-8)
lr1 = LrTDDFT(gs, xc=xc, txt='-')
lr1.diagonalize()
# check the oscillator strrength
assert (abs(lr1[0].get_oscillator_strength()[0] /
            lr[0].get_oscillator_strength()[0] -1) < 1e-10)

#print "-> reading gs without wfs"