示例#1
0
     model.geom_force_tol = tol
     model.geom_stress_tol = tol
     model.geom_energy_tol = 1.0e8
     model.geom_disp_tol = 1.0e8
     print "BOB relax atoms"
     at = relax_atoms_cell(at, tol=tol)
     i_minim = -1
     converged = True
 else:
     config_minim = UnitCellFilter(at)
     x = config_minim.get_positions()
     converged = False
     for i_minim in range(500):
         config_minim.set_positions(x)
         grad_f = -config_minim.get_forces()
         E = config_minim.get_potential_energy()
         try:
             pred_err = predictive_error(config_minim.atoms)
         except:
             pred_err = None
         if isinstance(config_minim, UnitCellFilter):
             print config_i, "SD2: {} {} {} {}".format(
                 i_minim, E, np.max(np.abs(grad_f[:n_at])),
                 np.max(np.abs(grad_f[n_at:])))
         else:
             print config_i, "SD2: {} {} {}".format(
                 i_minim, E, np.max(np.abs(grad_f[:n_at])))
         if np.max(np.abs(grad_f[:n_at])) < tol and np.max(
                 np.abs(grad_f[n_at:])) < tol:
             converged = True
             break
示例#2
0
def struct_energy(e0_per_atom, filename):
    V_unrel = []
    V_rel = []
    E_unrel = []
    E_rel = []

    ats = ase.io.read(os.path.dirname(__file__) + "/" + filename,
                      index=':',
                      format='extxyz')
    for (i, at_orig) in enumerate(ats):
        at = at_orig.copy()
        at.set_calculator(model.calculator)
        # # The commented out bit that follows seems to break CASTEP_file - no minimization runs are set up, apparently because call to relax_atoms_cell doesn't actually trigger a calculate()
        # unrelaxed_e_per_atom  = at.get_potential_energy()/len(at)
        # print 'at unrelaxed energy per atom', unrelaxed_e_per_atom
        # E_unrel.append(unrelaxed_e_per_atom-e0_per_atom)

        # relax fully
        print "BOB: calling relax_atoms_cell"
        if os.path.basename(os.path.dirname(model.__file__)) == 'CASTEP_file':
            at = relax_atoms_cell(at,
                                  tol=fmax,
                                  traj_file="model-" + model.name +
                                  "-RSS-{}-".format(i) + filename +
                                  "-relaxed.opt.xyz")
        else:
            n_at = len(at)
            config_minim = UnitCellFilter(at)
            x = config_minim.get_positions()
            converged = False
            for i_minim in range(500):
                config_minim.set_positions(x)
                grad_f = -config_minim.get_forces()
                E = config_minim.get_potential_energy()
                try:
                    pred_err = predictive_error(config_minim.atoms)
                except:
                    pred_err = None
                if isinstance(config_minim, UnitCellFilter):
                    print i, "SD2: {} {} {} {}".format(
                        i_minim, E, np.max(np.abs(grad_f[:n_at])),
                        np.max(np.abs(grad_f[n_at:])))
                else:
                    print i, "SD2: {} {} {}".format(
                        i_minim, E, np.max(np.abs(grad_f[:n_at])))
                if np.max(np.abs(grad_f[:n_at])) < fmax and np.max(
                        np.abs(grad_f[n_at:])) < fmax:
                    converged = True
                    break
                if i_minim == 0:
                    alpha = 1.0e-6
                else:
                    alpha = np.sum(
                        (x - x_old) * (grad_f - grad_f_old)) / np.sum(
                            (grad_f - grad_f_old)**2)
                x_old = x.copy()
                grad_f_old = grad_f.copy()
                x -= np.abs(alpha) * grad_f
        print "BOB: done relax_atoms_cell"
        ase.io.write(sys.stdout, at, format='extxyz')

        print "BOB: calling get_potential_energy for relaxed"
        relaxed_e_per_atom = at.get_potential_energy() / len(at)
        print "BOB: done get_potential_energy for relaxed"
        print 'at relaxed energy per atom', relaxed_e_per_atom
        E_rel.append(relaxed_e_per_atom - e0_per_atom)

        V_rel.append(at.get_volume() / len(at))

    # This is a workaround for the problem mentioned above
    ats = ase.io.read(os.path.dirname(__file__) + "/" + filename,
                      index=':',
                      format='extxyz')
    for (i, at) in enumerate(ats):
        at.set_calculator(model.calculator)

        # relax fully
        print "BOB: calling get_potential_energy for unrelaxed"
        unrelaxed_e_per_atom = at.get_potential_energy() / len(at)
        print "BOB: done get_potential_energy for unrelaxed"
        print 'at unrelaxed energy per atom', unrelaxed_e_per_atom
        E_unrel.append(unrelaxed_e_per_atom - e0_per_atom)
        V_unrel.append(at.get_volume() / len(at))
    # end of workaround

    return (V_unrel, E_unrel, V_rel, E_rel)