Ejemplo n.º 1
0
 def f(p, name):
     if atoms.calc.wfs.world.rank == 0:
         gen = _generate(**p)
         gen.make_paw_setup(name).write_xml()
     atoms.calc.wfs.world.barrier()
     atoms.calc.set(setups={None: 'derivative0', p['symbol']: name})
     e = atoms.get_potential_energy()
     return e
Ejemplo n.º 2
0
 def f(p, name):
     if atoms.calc.wfs.world.rank == 0:
         gen = _generate(**p)
         gen.make_paw_setup(name).write_xml()
     atoms.calc.wfs.world.barrier()
     atoms.calc.set(setups={None: 'derivative0', p['symbol']: name})
     e = atoms.get_potential_energy()
     return e
Ejemplo n.º 3
0
    def generate(self,
                 fd,
                 xc,
                 projectors,
                 radii,
                 r0,
                 scalar_relativistic=False,
                 tag=None,
                 logderivs=True):
        if self.old:
            self.generate_old(fd, xc, scalar_relativistic, tag)
            return 0.0

        if projectors[-1].isupper():
            nderiv0 = 5
        else:
            nderiv0 = 2

        type = 'poly'
        if self.nc:
            type = 'nc'
        gen = _generate(self.symbol, xc, self.conf, projectors, radii,
                        scalar_relativistic, None, r0, nderiv0, (type, 4),
                        None, None, fd)
        if not scalar_relativistic:
            if not gen.check_all():
                print('dataset check failed')
                return np.inf

        if tag is not None:
            gen.make_paw_setup(tag or None).write_xml()

        r = 1.1 * gen.rcmax

        lmax = 2
        if 'f' in projectors:
            lmax = 3

        error = 0.0
        if logderivs:
            for l in range(lmax + 1):
                emin = -1.5
                emax = 2.0
                n0 = gen.number_of_core_states(l)
                if n0 > 0:
                    e0_n = gen.aea.channels[l].e_n
                    emin = max(emin, e0_n[n0 - 1] + 0.1)
                energies = np.linspace(emin, emax, 100)
                de = energies[1] - energies[0]
                ld1 = gen.aea.logarithmic_derivative(l, energies, r)
                ld2 = gen.logarithmic_derivative(l, energies, r)
                error += abs(ld1 - ld2).sum() * de

        return error
Ejemplo n.º 4
0
def derivatives(atoms):
    """Calculate derivatives of the energy with respect to PAW-setup
    parameters."""

    e00 = atoms.get_potential_energy()

    allsetups = atoms.calc.wfs.setups.setups

    parameters = {}
    for setup in allsetups.values():
        d = setup.data
        projectors = []
        radii = []
        ll = -1
        for n, l, e, r in zip(d.n_j, d.l_j, d.eps_j, d.rcut_j):
            if l > ll:
                radii.append(r)
                ll = l
            if n > 0:
                e = n
            projectors.append('%r%s' % (e, 'spdfg'[l]))

        kwargs = dict(symbol=d.symbol,
                      xc=d.xcname,
                      projectors=','.join(projectors),
                      radii=radii,
                      scalar_relativistic=(d.type == 'scalar-relativistic'),
                      alpha=1 / d.rcgauss**2,
                      gamma=d.gamma,
                      h=d.h,
                      l0=d.l0,
                      r0=d.r0,
                      nderiv0=d.nderiv0,
                      e0=d.e0)
        parameters[d.symbol] = kwargs

    for symbol, p in parameters.items():
        if atoms.calc.wfs.world.rank == 0:
            gen = _generate(**p)
            gen.make_paw_setup('derivative0').write_xml()
        atoms.calc.wfs.world.barrier()

    atoms.calc.set(setups='derivative0')
    e0 = atoms.get_potential_energy()

    def f(p, name):
        if atoms.calc.wfs.world.rank == 0:
            gen = _generate(**p)
            gen.make_paw_setup(name).write_xml()
        atoms.calc.wfs.world.barrier()
        atoms.calc.set(setups={None: 'derivative0', p['symbol']: name})
        e = atoms.get_potential_energy()
        return e

    results = {}
    for symbol, p in parameters.items():
        derivs = []
        for i, r in enumerate(p['radii']):
            p['radii'][i] = 1.01 * r
            e = f(p, 'derivative_rc%d' % i)
            derivs.append((e - e0) / (0.01 * r))
            p['radii'][i] = r

        alpha = p['alpha']
        p['alpha'] = 1.01 * alpha
        e = f(p, 'derivative_alpha')
        derivs.append((e - e0) / (0.01 * alpha))
        p['alpha'] = alpha

        r0 = p['r0']
        p['r0'] = 1.01 * r0
        e = f(p, 'derivative_r0')
        derivs.append((e - e0) / (0.01 * r0))
        p['r0'] = r0

        results[symbol] = derivs

    return results
Ejemplo n.º 5
0
def derivatives(atoms):
    """Calculate derivatives of the energy with respect to PAW-setup
    parameters."""

    e00 = atoms.get_potential_energy()

    allsetups = atoms.calc.wfs.setups.setups

    parameters = {}
    for setup in allsetups.values():
        d = setup.data
        projectors = []
        radii = []
        ll = -1
        for n, l, e, r in zip(d.n_j, d.l_j, d.eps_j, d.rcut_j):
            if l > ll:
                radii.append(r)
                ll = l
            if n > 0:
                e = n
            projectors.append('%r%s' % (e, 'spdfg'[l]))

        kwargs = dict(symbol=d.symbol,
                      xc=d.xcname,
                      projectors=','.join(projectors),
                      radii=radii,
                      scalar_relativistic=(d.type == 'scalar-relativistic'),
                      alpha=1 / d.rcgauss**2,
                      gamma=d.gamma,
                      h=d.h,
                      l0=d.l0,
                      r0=d.r0,
                      nderiv0=d.nderiv0,
                      e0=d.e0)
        parameters[d.symbol] = kwargs

    
    for symbol, p in parameters.items():
        if atoms.calc.wfs.world.rank == 0:
            gen = _generate(**p)
            gen.make_paw_setup('derivative0').write_xml()
        atoms.calc.wfs.world.barrier()
        
    atoms.calc.set(setups='derivative0')
    e0 = atoms.get_potential_energy()
    
    def f(p, name):
        if atoms.calc.wfs.world.rank == 0:
            gen = _generate(**p)
            gen.make_paw_setup(name).write_xml()
        atoms.calc.wfs.world.barrier()
        atoms.calc.set(setups={None: 'derivative0', p['symbol']: name})
        e = atoms.get_potential_energy()
        return e

    results = {}
    for symbol, p in parameters.items():
        derivs = []
        for i, r in enumerate(p['radii']):
            p['radii'][i] = 1.01 * r
            e = f(p, 'derivative_rc%d' % i)
            derivs.append((e - e0) / (0.01 * r))
            p['radii'][i] = r

        alpha = p['alpha']
        p['alpha'] = 1.01 * alpha
        e = f(p, 'derivative_alpha')
        derivs.append((e - e0) / (0.01 * alpha))
        p['alpha'] = alpha

        r0 = p['r0']
        p['r0'] = 1.01 * r0
        e = f(p, 'derivative_r0')
        derivs.append((e - e0) / (0.01 * r0))
        p['r0'] = r0

        results[symbol] = derivs

    return results