def __init__(self, restart=None, state=0, rng=np.random): self.rng = rng MorsePotential.__init__(self, restart=restart, epsilon=De[state], r0=Re[state], rho0=rho0[state])
def calculate(self, atoms=None, properties=['energy'], system_changes=all_changes): if atoms is not None: assert len(atoms) == 2 MorsePotential.calculate(self, atoms, properties, system_changes) # determine 'wave functions' including # Berry phase (arbitrary sign) and # random orientation of wave functions perpendicular # to the molecular axis # molecular axis vr = atoms[1].position - atoms[0].position r = np.linalg.norm(vr) hr = vr / r # perpendicular axes vrand = self.rng.rand(3) hx = np.cross(hr, vrand) hx /= np.linalg.norm(hx) hy = np.cross(hr, hx) hy /= np.linalg.norm(hy) wfs = [1, hr, hx, hy] # Berry phase berry = (-1)**self.rng.randint(0, 2, 4) self.wfs = [wf * b for wf, b in zip(wfs, berry)]
def test_morse_cluster(internal, order, trajectory=None): rng = np.random.RandomState(4) nat = 4 atoms = Atoms(['Xe'] * nat, rng.normal(size=(nat, 3), scale=3.0)) # parameters from DOI: 10.1515/zna-1987-0505 atoms.calc = MorsePotential(alpha=226.9 * kB, r0=4.73, rho0=4.73 * 1.099) cons = Constraints(atoms) cons.fix_translation() cons.fix_rotation() opt = Sella( atoms, order=order, internal=internal, trajectory=trajectory, gamma=1e-3, constraints=cons, ) opt.run(fmax=1e-3) Ufree = opt.pes.get_Ufree() np.testing.assert_allclose(opt.pes.get_g() @ Ufree, 0, atol=5e-3) opt.pes.diag(gamma=1e-16) H = opt.pes.get_HL().project(Ufree) assert np.sum(H.evals < 0) == order, H.evals
def test_example(): from ase import Atoms from ase.constraints import FixAtoms from ase.io import Trajectory from ase.optimize import QuasiNewton from ase.calculators.morse import MorsePotential atoms = Atoms('H7', positions=[(0, 0, 0), (1, 0, 0), (0, 1, 0), (1, 1, 0), (0, 2, 0), (1, 2, 0), (0.5, 0.5, 1)], constraint=[FixAtoms(range(6))], calculator=MorsePotential()) traj = Trajectory('H.traj', 'w', atoms) dyn = QuasiNewton(atoms, maxstep=0.2) dyn.attach(traj.write) dyn.run(fmax=0.01, steps=100) print(atoms) del atoms[-1] print(atoms) del atoms[5] print(atoms) assert len(atoms.constraints[0].index) == 5
def test_forces(): atoms = bulk('Cu', cubic=True) atoms.calc = MorsePotential(A=4.0, epsilon=1.0, r0=2.55) atoms.rattle(0.1) forces = atoms.get_forces() numerical_forces = atoms.calc.calculate_numerical_forces(atoms, d=1e-5) assert np.abs(forces - numerical_forces).max() < 1e-5
def run_neb_calculation(cpu): images = [PickleTrajectory('H.traj')[-1]] for i in range(nimages): images.append(images[0].copy()) images[-1].positions[6, 1] = 2 - images[0].positions[6, 1] neb = NEB(images, parallel=True, world=cpu) neb.interpolate() images[cpu.rank + 1].set_calculator(MorsePotential()) dyn = BFGS(neb) dyn.run(fmax=fmax) if cpu.rank == 1: results.append(images[2].get_potential_energy())
def test_example(testdir): atoms = Atoms('H7', positions=[(0, 0, 0), (1, 0, 0), (0, 1, 0), (1, 1, 0), (0, 2, 0), (1, 2, 0), (0.5, 0.5, 1)], constraint=[FixAtoms(range(6))], calculator=MorsePotential()) with Trajectory('H.traj', 'w', atoms) as traj, \ QuasiNewton(atoms, maxstep=0.2) as dyn: dyn.attach(traj.write) dyn.run(fmax=0.01, steps=100) print(atoms) del atoms[-1] print(atoms) del atoms[5] print(atoms) assert len(atoms.constraints[0].index) == 5
def initialize(image, imagenum, new_opt, get_filename): """Initialize the image and return the trajectory name.""" if get_filename: return 'cogef' + str(imagenum) + '.traj' image.set_calculator(MorsePotential())
from ase import Atoms from ase.constraints import FixAtoms from ase.io import Trajectory, read from ase.neb import NEB, NEBTools from ase.calculators.morse import MorsePotential from ase.optimize import BFGS, QuasiNewton atoms = Atoms('H7', positions=[(0, 0, 0), (1, 0, 0), (0, 1, 0), (1, 1, 0), (0, 2, 0), (1, 2, 0), (0.5, 0.5, 1)], constraint=[FixAtoms(range(6))], calculator=MorsePotential()) traj = Trajectory('H.traj', 'w', atoms) dyn = QuasiNewton(atoms, maxstep=0.2) dyn.attach(traj.write) dyn.run(fmax=0.01, steps=100) print(atoms) del atoms[-1] print(atoms) del atoms[5] print(atoms) assert len(atoms.constraints[0].index) == 5 fmax = 0.05 nimages = 3 print([a.get_potential_energy() for a in Trajectory('H.traj')]) images = [Trajectory('H.traj')[-1]] for i in range(nimages):
p0 = np.array((0., 0., 8.)) box = [p0, [v1, v2, v3]] stoichiometry = 5 * [22] + 10 * [8] print 'slab', buildFeature(slab, 6, [8, 22]) dmin = closest_distances_generator(atom_numbers=[22, 8], ratio_of_covalent_radii=0.6) sg = StartGenerator( slab=slab, # Generator to generate initial structures atom_numbers=stoichiometry, closest_allowed_distances=dmin, box_to_place_in=box) calc = MorsePotential() test = sg.get_new_candidate() test.set_calculator(calc) test.info['confid'] = 1 view(test) cd = ClusterDistanceMutation(slab, len(stoichiometry), dmin, 5, 1, verbose=True) res, desc = cd.get_new_individual([test]) res.set_calculator(calc) view(res) res.info['confid'] = 2
def calc(): return MorsePotential(A=4.0, epsilon=1.0, r0=2.55)
def __init__(self, state): MorsePotential.__init__(self, epsilon=De[state], r0=Re[state], rho0=rho0[state])
def initialize(image, imagenum, new_opt, get_filename): #function required for cogef.pull """Initialize the image and return the trajectory name.""" if get_filename: return 'cogef_coia' + str(imagenum) + '.traj' image.set_calculator(MorsePotential())
r0 = 1.5 alpha = 0.3 # These are the distances between the atoms for which we evaluate the energy distances = numpy.linspace( 0.0, 10, 50) # creates an array of 24 equidistant points between 0.2 and 2.5 energies = [] # we calculate the energy of the system for each distances in the distances array for d in distances: # iterates over all distances structure = ase.Atoms('H2', positions=[[0, 0, 0], [ 0, 0, d ]]) # creates the particle system for the specific distance structure.set_calculator( MorsePotential(epsilon=D, rho0=alpha * r0, r0=r0) ) # determines how the interaction is calculated between the particles energies.append(structure.get_potential_energy( )) # calculates and appends the current energy to the array of energies if d == distances[0]: write('traj.xyz', structure, append=False ) # writes the first configuration to the trajectory file else: write( 'traj.xyz', structure, append=True) # appends all other configurations to trajectory file print(distances, energies) plt.plot(distances, energies, 'o--') # plots the energies vs distances plt.savefig("traja.pdf")
from cogef import COGEF, Dissociation import pylab as plt #cute shortcut for matplotlib~ (and numpy?) def initialize(image, imagenum, new_opt, get_filename): """Initialize the image and return the trajectory name.""" if get_filename: return 'cogef' + str(imagenum) + '.traj' image.set_calculator(MorsePotential()) fmax = 0.05 image = Atoms('H10', positions=[(i, 0, 0) for i in range(10)]) image.set_calculator( MorsePotential()) #set calculation theory. Morse used as placeholder. FIRE(image).run(fmax=fmax) cogef = COGEF([image], 0, 8, optimizer=FIRE, fmax=fmax) #relax atoms through cogef using optimizer stepsize = 0.03 steps = 35 cogef.pull(stepsize, steps, initialize, 'cogef.traj') #simulate pulling apart of atoms energies, distances = cogef.get_energy_curve( ) #calculate energy and distance from cogef run plt.figure(0) #create figure (empty) plt.plot(distances, energies) #make plot plt.xlabel('d [$\\AA$]') #set x axis label
def test_gs_minimum_energy(): atoms = Atoms('H2', positions=[[0, 0, 0], [0, 0, Re]]) atoms.calc = MorsePotential(epsilon=De, r0=Re) assert atoms.get_potential_energy() == -De
def test_gs_vibrations(): # check ground state vibrations atoms = Atoms('H2', positions=[[0, 0, 0], [0, 0, Re]]) atoms.calc = MorsePotential(epsilon=De, r0=Re, rho0=rho0) vib = Vibrations(atoms) vib.run()
def main(geom): nifty.printcool(" Building the LOT") lot = ASELoT.from_options(MorsePotential(), geom=geom) nifty.printcool(" Building the PES") pes = PES.from_options( lot=lot, ad_idx=0, multiplicity=1, ) nifty.printcool("Building the topology") atom_symbols = manage_xyz.get_atoms(geom) ELEMENT_TABLE = elements.ElementData() atoms = [ELEMENT_TABLE.from_symbol(atom) for atom in atom_symbols] # top = Topology.build_topology( # xyz, # atoms, # ) # nifty.printcool("Building Primitive Internal Coordinates") # p1 = PrimitiveInternalCoordinates.from_options( # xyz=xyz, # atoms=atoms, # addtr=False, # Add TRIC # topology=top, # ) nifty.printcool("Building Delocalized Internal Coordinates") coord_obj1 = DelocalizedInternalCoordinates.from_options( xyz=xyz, atoms=atoms, addtr=False, # Add TRIC ) nifty.printcool("Building Molecule") reactant = Molecule.from_options( geom=geom, PES=pes, coord_obj=coord_obj1, Form_Hessian=True, ) nifty.printcool("Creating optimizer") optimizer = eigenvector_follow.from_options(Linesearch='backtrack', OPTTHRESH=0.0005, DMAX=0.5, abs_max_step=0.5, conv_Ediff=0.5) nifty.printcool("initial energy is {:5.4f} kcal/mol".format( reactant.energy)) geoms, energies = optimizer.optimize( molecule=reactant, refE=reactant.energy, opt_steps=500, verbose=True, ) nifty.printcool("Final energy is {:5.4f}".format(reactant.energy)) manage_xyz.write_xyz('minimized.xyz', geoms[-1], energies[-1], scale=1.)
from ase import Atoms from ase.constraints import FixAtoms from ase.io import Trajectory from ase.optimize import QuasiNewton from ase.calculators.morse import MorsePotential atoms = Atoms('H7', positions=[(0, 0, 0), (1, 0, 0), (0, 1, 0), (1, 1, 0), (0, 2, 0), (1, 2, 0), (0.5, 0.5, 1)], constraint=[FixAtoms(range(6))], calculator=MorsePotential()) traj = Trajectory('H.traj', 'w', atoms) dyn = QuasiNewton(atoms, maxstep=0.2) dyn.attach(traj.write) dyn.run(fmax=0.01, steps=100) print(atoms) del atoms[-1] print(atoms) del atoms[5] print(atoms) assert len(atoms.constraints[0].index) == 5
def gen_potential_data(args, data_count=100, atom_count=2, side_len=20, interval=10): input_lst = [] tgt_lst = [] atoms_lst = [] postv = data_count/2 negtv = data_count/2 while(len(atoms_lst) < data_count): print('current data size is: ', len(atoms_lst)) last_engy = 0 atom_coords = [] atoms = Atoms() # atoms.append(Atom('Au', (0.5, 0.5, 0.5))) atoms.append(Atom('Au', (0, 0, 0))) for _ in range(atom_count-1): x = random.random() * side_len y = random.random() * side_len z = random.random() * side_len atoms.append(Atom('Au', (x, y, z))) morse_calc = MorsePotential() atoms.set_calculator(morse_calc) dyn = BFGS(atoms, trajectory='latest_relax.traj') dyn.run(fmax=0.1, steps=100) traj = Trajectory('latest_relax.traj') for atoms in traj: cur_engy = atoms.get_potential_energy() if args.task == 'reg': if cur_engy < -0.01 and abs(last_engy-cur_engy) > 1: atoms_lst.append(atoms) last_engy = cur_engy elif args.task == 'cls': if cur_engy < 0 and negtv > 0: negtv -= 1 atoms_lst.append(atoms) elif cur_engy > 0 and postv > 0: postv -= 1 atoms_lst.append(atoms) else: pass else: pass random.shuffle(atoms_lst) for i in range(len(atoms_lst)): atom_coords = list(atoms_lst[i].positions) engy = atoms_lst[i].get_potential_energy() input_lst.append(atom_coords) if args.task == 'reg': tgt_lst.append(engy) elif args.task == 'cls': if engy < 0: tgt_lst.append(0) else: tgt_lst.append(1) else: pass if args.task == 'reg': # normalize tgt_lst = np.array(tgt_lst) tgt_lst /= max(abs(tgt_lst)) tgt_lst = tgt_lst.tolist() return input_lst, tgt_lst
def calc(): # Common calculator for all images. return MorsePotential()