def ase_minimization(indiv, Optimizer): """Function to use built in ASE minimizers to minimize atomic positions in structure. Input: indiv = Individual class object to be optimized Optimizer = Optimizer class object with needed parameters Output: indiv = Optimized Individual class object. """ if 'MU' in Optimizer.debug: debug = True else: debug = False cwd1=os.getcwd() olammpsmin = Optimizer.lammps_min if Optimizer.lammps_min: Optimizer.lammps_min = None calc2 = setup_calculator(Optimizer) # if 'mass' in indiv[0].get_calculator(): # mass2 = ['1 '+ str(Optimizer.atomlist[0][2])] # if len(Optimizer.atomlist) > 1: # for i in range(len(Optimizer.atomlist)-1): # mass2.append(str(i+2) + ' ' + str(Optimizer.atomlist[i+1][2])) # calc2=LAMMPS(parameters={ 'pair_style' : Optimizer.pair_style, 'pair_coeff' : Optimizer.pair_coeff , 'mass' : mass2 },files=[ Optimizer.pot_file ]) # else: # calc2=LAMMPS(parameters={ 'pair_style' : Optimizer.pair_style, 'pair_coeff' : Optimizer.pair_coeff},files=[ Optimizer.pot_file ]) if Optimizer.structure==Defect: nat=indiv[0].get_number_of_atoms sol=Atoms() sol.extend(indiv[0]) sol.extend(indiv.bulko) sol.set_calculator(calc2) sol.set_cell(indiv.bulko.get_cell()) sol.set_pbc(True) dyn=BFGS(sol) dyn.run(fmax=0.001, steps=2500) positions=sol[0:nat].get_positions() indiv[0].set_positions(positions) else: atomsdup=indiv[0].copy() atomsdup.set_calculator(calc2) dyn=BFGS(indiv[0]) dyn.run(fmax=0.001, steps=2500) positions=atomsdup.get_positions() indiv[0].set_positions(positions) os.chdir(cwd1) calc2.clean() Optimizer.lammps_min = olammpsmin Optimizer.output.write('ASE Minimization mutation performed on individual = '+repr(indiv.index)+'\n') muttype='ASEM' if indiv.energy==0: indiv.history_index=indiv.history_index+'m'+muttype else: indiv.history_index=repr(indiv.index)+'m'+muttype return indiv
def get_defect_indiv_random(Optimizer): """ Function to generate a structopt Individual class structure with a defect structure. Inputs: Optimizer = structopt Optimizer class object Outputs: individ = structopt Individual class object containing defect structure data """ #Initialize Bulk - Generate or load positions of bulk solid if not Optimizer.solidbulk: if 'Island_Method' not in Optimizer.algorithm_type: outfilename = os.path.join( os.path.join(os.getcwd(), Optimizer.filename), 'Bulkfile.xyz') else: from mpi4py import MPI rank = MPI.COMM_WORLD.Get_rank() outfilename = os.path.join( os.path.join(os.getcwd(), Optimizer.filename + '-rank' + repr(rank)), 'Bulkfile.xyz') if Optimizer.evalsolid: if Optimizer.parallel: from MAST.structopt.tools.setup_calculator import setup_calculator Optimizer.calc = setup_calculator(Optimizer) bulk1, PureBulkEnpa, stro = gen_solid(Optimizer.solidfile, Optimizer.solidcell, outfilename, Optimizer.calc, Optimizer.calc_method) Optimizer.output.write(stro) else: bulk1 = gen_solid(Optimizer.solidfile, Optimizer.solidcell, outfilename) PureBulkEnpa = 0 natomsbulk = len(bulk1) Optimizer.solidbulk = bulk1.copy() Optimizer.purebulkenpa = PureBulkEnpa Optimizer.natomsbulk = natomsbulk # Identify nearby atoms for region 2 inclusion bulk = Optimizer.solidbulk.copy() bulkcom = bulk.get_center_of_mass() bulk.translate(-bulkcom) if Optimizer.sf != 0: bulk.append(Atom(position=[0, 0, 0])) nbulk = Atoms(pbc=True, cell=bulk.get_cell()) nr2 = Atoms(pbc=True, cell=bulk.get_cell()) for i in range(len(bulk) - 1): dist = bulk.get_distance(-1, i) if dist <= Optimizer.sf: nr2.append(bulk[i]) else: nbulk.append(bulk[i]) else: nbulk = bulk.copy() nr2 = Atoms(pbc=True, cell=bulk.get_cell()) #Update atom list with atoms in region 2 natlist = [] for sym, c, m, u in Optimizer.atomlist: atsym = [atm for atm in nr2 if atm.symbol == sym] natlist.append((sym, len(atsym), m, u)) # Generate random individual and region 2 if 'sphere' in Optimizer.generate_flag: ind = gen_pop_sphere(Optimizer.atomlist, Optimizer.size) elif 'dumbbell' in Optimizer.generate_flag: ind = Atoms(cell=[Optimizer.size for i in range(3)], pbc=True) for sym, c, m, u in Optimizer.atomlist: if c > 0: dums = generate_dumbbells(c, dumbbellsym=sym, nindiv=1, solid=Optimizer.solidbulk, size=Optimizer.size)[0] ind.extend(dums) else: ind = gen_pop_box(Optimizer.atomlist, Optimizer.size) nnr2 = gen_pop_sphere(natlist, Optimizer.sf * 2.0) nnr2.translate([-Optimizer.sf, -Optimizer.sf, -Optimizer.sf]) nnr2.set_pbc(True) nnr2.set_cell(bulk.get_cell()) # Initialize class individual with known values individ = Individual(ind) individ.purebulkenpa = Optimizer.purebulkenpa individ.natomsbulk = Optimizer.natomsbulk # Combine individual with R2 icom = ind.get_center_of_mass() ind.translate(-icom) ind.extend(nnr2) ind.set_pbc(True) ind.set_cell(bulk.get_cell()) # Recenter structure nbulk.translate(bulkcom) ind.translate(bulkcom) individ[0] = ind.copy() individ.bulki = nbulk.copy() individ.bulko = nbulk.copy() bulk = nbulk.copy() bul = bulk.copy() for atm in individ[0]: bul.append(atm) indices = [] for sym, c, m, u in Optimizer.atomlist: if c < 0: if Optimizer.randvacst: alist = [one for one in bul if one.symbol == sym] count = abs(c) while count > 0: indices.append(random.choice(alist).index) count -= 1 else: pos = individ[0][0:Optimizer.natoms].get_center_of_mass() count = abs(c) bul.append(Atom(position=pos)) alist = [one for one in bul if one.symbol == sym] alistd = [(bul.get_distance(len(bul) - 1, one.index), one.index) for one in alist] alistd.sort(reverse=True) bul.pop() while count > 0: idx = alistd.pop()[1] indices.append(idx) count -= 1 if len(indices) != 0: nbulklist = [ at for at in bul if at.index not in indices and at.index < len(bulk) ] nalist = [ at for at in bul if at.index not in indices and at.index >= len(bulk) ] bulkn = Atoms(cell=bulk.get_cell(), pbc=True) for atm in nbulklist: bulkn.append(atm) individ.bulki = bulkn.copy() individ.bulko = bulkn.copy() newind = Atoms() for atm in nalist: newind.append(atm) newind.set_cell(individ[0].get_cell()) newind.set_pbc(True) individ[0] = newind return individ
def eval_energy(Optimizer, individ): """Function to evaluate energy of an individual Inputs: input = [Optimizer class object with parameters, Individual class structure to be evaluated] Outputs: energy, bul, individ, signal energy = energy of Individual evaluated bul = bulk structure of Individual if simulation structure is Defect individ = Individual class structure evaluated signal = string of information about evaluation """ #logger = initialize_logger(Optimizer.loggername) logger = logging.getLogger(Optimizer.loggername) if 'MAST' in Optimizer.calc_method: energy = individ.energy bul = individ.bulki signal = 'Received MAST structure\n' logger.info( 'Received individual index = {0} from MAST with energy {1}. Returning with no evaluation' .format(individ.index, individ.energy)) else: if Optimizer.parallel: rank = MPI.COMM_WORLD.Get_rank() logger.info( 'Received individual HI = {0} with energy {1} for energy evaluation' .format(individ.history_index, individ.energy)) STR = '----Individual ' + str( individ.history_index) + ' Optimization----\n' indiv = individ[0] if 'EE' in Optimizer.debug: debug = True else: debug = False if debug: write_xyz(Optimizer.debugfile, indiv, 'Received by eval_energy') Optimizer.debugfile.flush() logger.debug('Writing recieved individual to debug file') # Establish individual structure for evaluation. Piece together regions when necessary. if Optimizer.structure == 'Defect': indi = indiv.copy() bulk = individ.bulki nat = indi.get_number_of_atoms() if debug: logger.info( 'Extending defect structure to include bulk len(r1+r2)={0} len(bulk)={1}' .format(nat, len(bulk))) csize = bulk.get_cell() totalsol = Atoms(cell=csize, pbc=True) totalsol.extend(indi) totalsol.extend(bulk) for sym, c, m, u in Optimizer.atomlist: nc = len([atm for atm in totalsol if atm.symbol == sym]) STR += 'Defect configuration contains ' + repr( nc) + ' ' + repr(sym) + ' atoms\n' elif Optimizer.structure == 'Surface': totalsol = Atoms() totalsol.extend(indiv) nat = indiv.get_number_of_atoms() totalsol.extend(individ.bulki) if debug: logger.info( 'Extending surface structure to include bulk len(r1+r2)={0} len(bulk)={1}' .format(nat, len(individ.bulki))) for sym, c, m, u in Optimizer.atomlist: nc = len([atm for atm in totalsol if atm.symbol == sym]) STR += 'Surface-Bulk configuration contains ' + repr( nc) + ' ' + repr(sym) + ' atoms\n' cell = numpy.maximum.reduce(indiv.get_cell()) totalsol.set_cell([cell[0], cell[1], 500]) totalsol.set_pbc([True, True, False]) elif Optimizer.structure == 'Cluster': totalsol = indiv.copy() nat = len(totalsol) if debug: logger.info( 'Extending cluster with {0} atoms to center of evaluation box of size {1}' .format(nat, Optimizer.large_box_size)) origcell = indiv.get_cell() totalsol.set_cell([ Optimizer.large_box_size, Optimizer.large_box_size, Optimizer.large_box_size ]) totalsol.translate([ Optimizer.large_box_size / 2.0, Optimizer.large_box_size / 2.0, Optimizer.large_box_size / 2.0 ]) elif Optimizer.structure == 'Crystal': totalsol = indiv.copy() nat = len(totalsol) else: print 'WARNING: In EvalEnergy. Optimizer.structure not recognized' logger.warning('Optimizer.structure not recognized') # Check for atoms that are too close or out of constrained location if Optimizer.constrain_position: if Optimizer.structure == 'Defect': if debug: logger.info('Constraining positions of defect') totalsol, stro = constrain_positions(totalsol, Optimizer.solidbulk, Optimizer.sf) if debug: logger.info(stro) STR += str0 min_len = 0.7 if not Optimizer.fixed_region: if debug: logger.info('Running check minimum distance') totalsol, STR = check_min_dist(totalsol, Optimizer.structure, nat, min_len, STR) if debug: write_xyz(Optimizer.debugfile, totalsol, 'After minlength check') Optimizer.debugfile.flush() logger.debug( 'Writing individual after checking minimum length') # Set calculator to use to get forces/energies if Optimizer.parallel: calc = setup_calculator(Optimizer) if Optimizer.fixed_region: if debug: logger.info('Setting up fixed region calculator') pms = copy.deepcopy(calc.parameters) try: pms['mass'][ len(pms['mass']) - 1] += '\ngroup RO id >= {0}\nfix freeze RO setforce 0.0 0.0 0.0\n'.format( nat) except KeyError: pms['pair_coeff'][ 0] += '\ngroup RO id >= {0}\nfix freeze RO setforce 0.0 0.0 0.0\n'.format( nat) calc = LAMMPS(parameters=pms, files=calc.files, keep_tmp_files=calc.keep_tmp_files, tmp_dir=calc.tmp_dir) lmin = copy.copy(Optimizer.lammps_min) if debug: logger.info('Setting up no local minimization calculator') Optimizer.lammps_min = None Optimizer.static_calc = setup_calculator(Optimizer) Optimizer.lammps_min = lmin else: calc = Optimizer.calc totalsol.set_calculator(calc) totalsol.set_pbc(True) # Perform Energy Minimization if not Optimizer.parallel: if debug: write_xyz(Optimizer.debugfile, totalsol, 'Individual sent to Energy Minimizer') logger.debug('Writing structure sent to energy minimizer') try: cwd = os.getcwd() if Optimizer.ase_min == True: if debug: logger.info('Running ASE minimizer') if Optimizer.calc_method == 'LennardJones': logger.warn('Must run ase LJ calculator with pbc=False') totalsol.set_pbc(False) totalsol, energy, pressure, volume, STR = run_ase_min( totalsol, Optimizer.ase_min_fmax, Optimizer.ase_min_maxsteps, Optimizer.fitness_scheme, STR) else: if debug: logger.info('Running local energy calculator') if Optimizer.fixed_region: totalsol, energy, pressure, volume, STR = run_energy_eval( totalsol, Optimizer.calc_method, Optimizer.fixed_region, Optimizer.fitness_scheme, STR, Optimizer.static_calc) else: totalsol, energy, pressure, volume, STR = run_energy_eval( totalsol, Optimizer.calc_method, False, Optimizer.fitness_scheme, STR) except Exception, e: logger.critical('Error in energy evaluation: {0}'.format(e), exc_info=True) path = os.path.join(cwd, 'TroubledLammps') if not os.path.exists(path): os.mkdir(path) #Copy files over shutil.copyfile( calc.trajfile, os.path.join(path, os.path.basename(calc.trajfile))) shutil.copyfile(calc.infile, os.path.join(path, os.path.basename(calc.infile))) shutil.copyfile(calc.logfile, os.path.join(path, os.path.basename(calc.logfile))) shutil.copyfile( calc.datafile, os.path.join(path, os.path.basename(calc.datafile))) raise RuntimeError('{0}:{1}'.format(Exception, e)) if not Optimizer.parallel: if debug: write_xyz(Optimizer.debugfile, totalsol, 'Individual after Energy Minimization') Optimizer.debugfile.flush() logger.debug( 'Writing structure recieved from energy minimizer') # Separate structures into distinct pieces if Optimizer.structure == 'Defect': if Optimizer.fixed_region == True or Optimizer.finddefects == False: if debug: logger.info( 'Identifying atoms in defect structure based on ID') individ[0] = totalsol[0:nat] bul = totalsol[(nat):len(totalsol)] individ[0].set_cell(csize) else: if debug: logger.info( 'Applying find defects scheme to identify R1 and R2 for Defect' ) if 'FD' in Optimizer.debug: outt = find_defects(totalsol, Optimizer.solidbulk, Optimizer.sf, atomlistcheck=Optimizer.atomlist, trackvacs=Optimizer.trackvacs, trackswaps=Optimizer.trackswaps, debug=Optimizer.debugfile) else: outt = find_defects(totalsol, Optimizer.solidbulk, Optimizer.sf, atomlistcheck=Optimizer.atomlist, trackvacs=Optimizer.trackvacs, trackswaps=Optimizer.trackswaps, debug=False) individ[0] = outt[0] bul = outt[1] individ.vacancies = outt[2] individ.swaps = outt[3] STR += outt[4] indiv = individ[0] elif Optimizer.structure == 'Surface': if debug: logger.info('Finding surface top layer') top, bul = find_top_layer(totalsol, Optimizer.surftopthick) indiv = top.copy() individ[0] = top.copy() bul = Atoms() elif Optimizer.structure == 'Crystal': if debug: logger.info('Checking crystal cell type') celltype = check_cell_type(totalsol) STR += 'Cell structure = {0}\n'.format(celltype) bul = Atoms() individ[0] = totalsol.copy() elif Optimizer.structure == 'Cluster': volume = get_cluster_volume(totalsol) bul = Atoms() if debug: logger.info( 'Translating cluster back to smaller box size location') totalsol.translate([ -Optimizer.large_box_size / 2.0, -Optimizer.large_box_size / 2.0, -Optimizer.large_box_size / 2.0 ]) totalsol.set_cell(origcell) individ[0] = totalsol.copy() # Add concentration energy dependence if Optimizer.forcing == 'energy_bias': if debug: logger.info( 'Applying energy bias for atoms with different number of atoms of type than in atomlist' ) n = [0] * len(Optimizer.atomlist) for i in range(len(Optimizer.atomlist)): n[i] = len([ inds for inds in totalsol if inds.symbol == Optimizer.atomlist[i][0] ]) n[i] = abs(n[i] - Optimizer.atomlist[i][1]) factor = sum(n)**3 energy = (energy + factor) / totalsol.get_number_of_atoms() STR += 'Energy with Bias = {0}\n'.format(energy) elif Optimizer.forcing == 'chem_pot': if debug: logger.info( 'Applying chemical potential bias for atoms with different number of atoms of type than in atomlist' ) n = [0] * len(Optimizer.atomlist) for i in range(len(Optimizer.atomlist)): n[i] = len([ inds for inds in totalsol if inds.symbol == Optimizer.atomlist[i][0] ]) n[i] = n[i] * Optimizer.atomlist[i][3] factor = sum(n) energy = (energy + factor) / totalsol.get_number_of_atoms() STR += 'Energy with Chemical Potential = {0}\n'.format(energy) individ.energy = energy individ.buli = bul individ.pressure = pressure individ.volume = volume if Optimizer.fingerprinting: if debug: logger.info('Identifying fingerprint of new structure') individ.fingerprint = get_fingerprint(Optimizer, individ, Optimizer.fpbin, Optimizer.fpcutoff) if Optimizer.parallel: calc.clean() signal = 'Evaluated individual {0} on {1}\n'.format( individ.index, rank) signal += STR else: signal = STR
def eval_energy(input): """Function to evaluate energy of an individual Inputs: input = [Optimizer class object with parameters, Individual class structure to be evaluated] Outputs: energy, bul, individ, signal energy = energy of Individual evaluated bul = bulk structure of Individual if simulation structure is Defect individ = Individual class structure evaluated signal = string of information about evaluation """ if input[0] == None: energy = 0 bul = 0 individ = 0 rank = MPI.COMM_WORLD.Get_rank() signal = 'Evaluated none individual on ' + repr(rank) + '\n' else: [Optimizer, individ] = input if Optimizer.calc_method == 'MAST': energy = individ.energy bul = individ.energy signal = 'Recieved MAST structure\n' else: if Optimizer.parallel: rank = MPI.COMM_WORLD.Get_rank() if not Optimizer.genealogy: STR = '----Individual ' + str( individ.index) + ' Optimization----\n' else: STR = '----Individual ' + str( individ.history_index) + ' Optimization----\n' indiv = individ[0] if 'EE' in Optimizer.debug: debug = True else: debug = False if debug: write_xyz(Optimizer.debugfile, indiv, 'Recieved by eval_energy') Optimizer.debugfile.flush() if Optimizer.structure == 'Defect': indi = indiv.copy() if Optimizer.alloy == True: bulk = individ.bulki else: bulk = individ.bulko nat = indi.get_number_of_atoms() csize = bulk.get_cell() totalsol = Atoms(cell=csize, pbc=True) totalsol.extend(indi) totalsol.extend(bulk) for sym, c, m, u in Optimizer.atomlist: nc = len([atm for atm in totalsol if atm.symbol == sym]) STR += 'Defect configuration contains ' + repr( nc) + ' ' + repr(sym) + ' atoms\n' elif Optimizer.structure == 'Surface': totalsol = Atoms() totalsol.extend(indiv) nat = indiv.get_number_of_atoms() totalsol.extend(individ.bulki) for sym, c, m, u in Optimizer.atomlist: nc = len([atm for atm in totalsol if atm.symbol == sym]) STR += 'Surface-Bulk configuration contains ' + repr( nc) + ' ' + repr(sym) + ' atoms\n' cell = numpy.maximum.reduce(indiv.get_cell()) totalsol.set_cell([cell[0], cell[1], 500]) totalsol.set_pbc([True, True, False]) if Optimizer.constrain_position: ts = totalsol.copy() indc, indb, vacant, swap, stro = find_defects( ts, Optimizer.solidbulk, 0) sbulk = Optimizer.solidbulk.copy() bcom = sbulk.get_center_of_mass() #totalsol.translate(-bulkcom) #indc.translate(-bulkcom) #totalsol.append(Atom(position=[0,0,0])) # for one in indc: # index = [atm.index for atm in totalsol if atm.position[0]==one.position[0] and atm.position[1]==one.position[1] and atm.position[2]==one.position[2]][0] # if totalsol.get_distance(-1,index) > Optimizer.sf: # r = random.random() # totalsol.set_distance(-1,index,Optimizer.sf*r,fix=0) # totalsol.pop() # totalsol.translate(bulkcom) com = indc.get_center_of_mass() dist = (sum((bcom[i] - com[i])**2 for i in range(3)))**0.5 if dist > Optimizer.sf: STR += 'Shifting structure to within region\n' r = random.random() * Optimizer.sf comv = numpy.linalg.norm(com) ncom = [one * r / comv for one in com] trans = [ncom[i] - com[i] for i in range(3)] indices = [] for one in indc: id = [ atm.index for atm in totalsol if atm.position[0] == one.position[0] and atm.position[1] == one.position[1] and atm.position[2] == one.position[2] ][0] totalsol[id].position += trans # Check for atoms that are too close min_len = 0.7 #pdb.set_trace() if not Optimizer.fixed_region: if Optimizer.structure == 'Defect' or Optimizer.structure == 'Surface': cutoffs = [2.0 for one in totalsol] nl = NeighborList(cutoffs, bothways=True, self_interaction=False) nl.update(totalsol) for one in totalsol[0:nat]: nbatoms = Atoms() nbatoms.append(one) indices, offsets = nl.get_neighbors(one.index) for index, d in zip(indices, offsets): index = int(index) sym = totalsol[index].symbol pos = totalsol[index].position + numpy.dot( d, totalsol.get_cell()) at = Atom(symbol=sym, position=pos) nbatoms.append(at) while True: dflag = False for i in range(1, len(nbatoms)): d = nbatoms.get_distance(0, i) if d < min_len: nbatoms.set_distance(0, i, min_len + .01, fix=0.5) STR += '--- WARNING: Atoms too close (<0.7A) - Implement Move ---\n' dflag = True if dflag == False: break for i in range(len(indices)): totalsol[indices[i]].position = nbatoms[i + 1].position totalsol[one.index].position = nbatoms[0].position nl.update(totalsol) if debug: write_xyz(Optimizer.debugfile, totalsol, 'After minlength check') Optimizer.debugfile.flush() else: for i in range(len(indiv)): for j in range(len(indiv)): if i != j: d = indiv.get_distance(i, j) if d < min_len: indiv.set_distance(i, j, min_len, fix=0.5) STR += '--- WARNING: Atoms too close (<0.7A) - Implement Move ---\n' if debug: write_xyz(Optimizer.debugfile, indiv, 'After minlength check') Optimizer.debugfile.flush() # Set calculator to use to get forces/energies if Optimizer.parallel: calc = setup_calculator(Optimizer) if Optimizer.fixed_region: pms = copy.deepcopy(calc.parameters) try: pms['mass'][ len(pms['mass']) - 1] += '\ngroup RO id >= ' + repr( nat) + '\nfix freeze RO setforce 0.0 0.0 0.0\n' except KeyError: pms['pair_coeff'][0] += '\ngroup RO id >= ' + repr( nat) + '\nfix freeze RO setforce 0.0 0.0 0.0\n' calc = LAMMPS(parameters=pms, files=calc.files, keep_tmp_files=calc.keep_tmp_files, tmp_dir=calc.tmp_dir) lmin = copy.copy(Optimizer.lammps_min) Optimizer.lammps_min = None Optimizer.static_calc = setup_calculator(Optimizer) Optimizer.lammps_min = lmin else: calc = Optimizer.calc if Optimizer.structure == 'Defect' or Optimizer.structure == 'Surface': totalsol.set_calculator(calc) totalsol.set_pbc(True) else: indiv.set_calculator(calc) indiv.set_pbc( True) #Current bug in ASE optimizer-Lammps prevents pbc=false if Optimizer.structure == 'Cluster': indiv.set_cell([500, 500, 500]) indiv.translate([250, 250, 250]) cwd = os.getcwd() # Perform Energy Minimization if not Optimizer.parallel: Optimizer.output.flush() if Optimizer.ase_min == True: try: if Optimizer.structure == 'Defect' or Optimizer.structure == 'Surface': dyn = BFGS(totalsol) else: dyn = BFGS(indiv) dyn.run(fmax=Optimizer.ase_min_fmax, steps=Optimizer.ase_min_maxsteps) except OverflowError: STR += '--- Error: Infinite Energy Calculated - Implement Random ---\n' box = Atoms() indiv = gen_pop_box(Optimizer.natoms, Optimizer.atomlist, Optimizer.size) indiv.set_calculator(calc) dyn = BFGS(indiv) dyn.run(fmax=fmax, steps=steps) except numpy.linalg.linalg.LinAlgError: STR += '--- Error: Singular Matrix - Implement Random ---\n' indiv = gen_pop_box(Optimizer.natoms, Optimizer.atomlist, Optimizer.size) indiv.set_calculator(calc) dyn = BFGS(indiv) dyn.run(fmax=fmax, steps=steps) # Get Energy of Minimized Structure if Optimizer.structure == 'Defect' or Optimizer.structure == 'Surface': en = totalsol.get_potential_energy() #force=numpy.maximum.reduce(abs(totalsol.get_forces())) if Optimizer.fitness_scheme == 'enthalpyfit': pressure = totalsol.get_isotropic_pressure( totalsol.get_stress()) cell_max = numpy.maximum.reduce(totalsol.get_positions()) cell_min = numpy.minimum.reduce(totalsol.get_positions()) cell = cell_max - cell_min volume = cell[0] * cell[1] * cell[2] else: pressure = 0 volume = 0 na = totalsol.get_number_of_atoms() ena = en / na energy = en individ[0] = totalsol[0:nat] bul = totalsol[(nat):len(totalsol)] STR += 'Number of positions = ' + repr( len(bul) + len(individ[0])) + '\n' individ[0].set_cell(csize) indiv = individ[0] else: en = indiv.get_potential_energy() if Optimizer.fitness_scheme == 'enthalpyfit': pressure = indiv.get_isotropic_pressure(indiv.get_stress()) cell_max = numpy.maximum.reduce(indiv.get_positions()) cell_min = numpy.minimum.reduce(indiv.get_positions()) cell = cell_max - cell_min volume = cell[0] * cell[1] * cell[2] else: pressure = 0 volume = 0 na = indiv.get_number_of_atoms() ena = en / na energy = ena individ[0] = indiv bul = 0 else: if Optimizer.structure == 'Defect' or Optimizer.structure == 'Surface': if Optimizer.calc_method == 'VASP': en = totalsol.get_potential_energy() calcb = Vasp(restart=True) totalsol = calcb.get_atoms() stress = calcb.read_stress() else: try: totcop = totalsol.copy() if debug: write_xyz(Optimizer.debugfile, totcop, 'Individual sent to lammps') OUT = totalsol.calc.calculate(totalsol) totalsol = OUT['atoms'] totalsol.set_pbc(True) if Optimizer.fixed_region: if debug: print 'Energy of fixed region calc = ', OUT[ 'thermo'][-1]['pe'] totalsol.set_calculator(Optimizer.static_calc) OUT = totalsol.calc.calculate(totalsol) totalsol = OUT['atoms'] totalsol.set_pbc(True) if debug: print 'Energy of static calc = ', OUT[ 'thermo'][-1]['pe'] en = OUT['thermo'][-1]['pe'] stress = numpy.array([ OUT['thermo'][-1][i] for i in ('pxx', 'pyy', 'pzz', 'pyz', 'pxz', 'pxy') ]) * (-1e-4 * GPa) #force=numpy.maximum.reduce(abs(totalsol.get_forces())) if debug: write_xyz(Optimizer.debugfile, totalsol, 'After Lammps Minimization') Optimizer.debugfile.flush() except Exception, e: os.chdir(cwd) STR += 'WARNING: Exception during energy eval:\n' + repr( e) + '\n' f = open('problem-structures.xyz', 'a') write_xyz(f, totcop, data='Starting structure hindex=' + individ.history_index) write_xyz(f, totalsol, data='Lammps Min structure') en = 10 stress = 0 f.close() if Optimizer.fitness_scheme == 'enthalpyfit': pressure = totalsol.get_isotropic_pressure(stress) cell_max = numpy.maximum.reduce(totalsol.get_positions()) cell_min = numpy.minimum.reduce(totalsol.get_positions()) cell = cell_max - cell_min volume = cell[0] * cell[1] * cell[2] else: pressure = totalsol.get_isotropic_pressure(stress) volume = 0 na = totalsol.get_number_of_atoms() ena = en / na energy = en if Optimizer.structure == 'Defect': if Optimizer.fixed_region == True or Optimizer.finddefects == False: individ[0] = totalsol[0:nat] bul = totalsol[(nat):len(totalsol)] individ[0].set_cell(csize) else: if 'FI' in Optimizer.debug: outt = find_defects( totalsol, Optimizer.solidbulk, Optimizer.sf, atomlistcheck=Optimizer.atomlist, trackvacs=Optimizer.trackvacs, trackswaps=Optimizer.trackswaps, debug=Optimizer.debugfile) else: outt = find_defects( totalsol, Optimizer.solidbulk, Optimizer.sf, atomlistcheck=Optimizer.atomlist, trackvacs=Optimizer.trackvacs, trackswaps=Optimizer.trackswaps, debug=False) individ[0] = outt[0] bul = outt[1] individ.vacancies = outt[2] individ.swaps = outt[3] STR += outt[4] indiv = individ[0] else: top, bul = find_top_layer(totalsol, Optimizer.surftopthick) indiv = top.copy() individ[0] = top.copy() else:
def eval_energy(Optimizer, individ): """Function to evaluate energy of an individual Inputs: input = [Optimizer class object with parameters, Individual class structure to be evaluated] Outputs: energy, bul, individ, signal energy = energy of Individual evaluated bul = bulk structure of Individual if simulation structure is Defect individ = Individual class structure evaluated signal = string of information about evaluation """ #logger = initialize_logger(Optimizer.loggername) logger = logging.getLogger(Optimizer.loggername) if 'MAST' in Optimizer.calc_method: energy = individ.energy bul = individ.bulki signal = 'Received MAST structure\n' logger.info('Received individual index = {0} from MAST with energy {1}. Returning with no evaluation'.format( individ.index, individ.energy)) else: if Optimizer.parallel: rank = MPI.COMM_WORLD.Get_rank() logger.info('Received individual HI = {0} with energy {1} for energy evaluation'.format( individ.history_index, individ.energy)) STR='----Individual ' + str(individ.history_index)+ ' Optimization----\n' indiv=individ[0] if 'EE' in Optimizer.debug: debug = True else: debug = False if debug: write_xyz(Optimizer.debugfile,indiv,'Received by eval_energy') Optimizer.debugfile.flush() logger.debug('Writing recieved individual to debug file') # Establish individual structure for evaluation. Piece together regions when necessary. if Optimizer.structure=='Defect': indi=indiv.copy() bulk=individ.bulki nat=indi.get_number_of_atoms() if debug: logger.info('Extending defect structure to include bulk len(r1+r2)={0} len(bulk)={1}'.format(nat,len(bulk))) csize=bulk.get_cell() totalsol=Atoms(cell=csize, pbc=True) totalsol.extend(indi) totalsol.extend(bulk) for sym,c,m,u in Optimizer.atomlist: nc=len([atm for atm in totalsol if atm.symbol==sym]) STR+='Defect configuration contains '+repr(nc)+' '+repr(sym)+' atoms\n' elif Optimizer.structure=='Surface': totalsol=Atoms() totalsol.extend(indiv) nat=indiv.get_number_of_atoms() totalsol.extend(individ.bulki) if debug: logger.info('Extending surface structure to include bulk len(r1+r2)={0} len(bulk)={1}'.format(nat,len(individ.bulki))) for sym,c,m,u in Optimizer.atomlist: nc=len([atm for atm in totalsol if atm.symbol==sym]) STR+='Surface-Bulk configuration contains '+repr(nc)+' '+repr(sym)+' atoms\n' cell=numpy.maximum.reduce(indiv.get_cell()) totalsol.set_cell([cell[0],cell[1],500]) totalsol.set_pbc([True,True,False]) elif Optimizer.structure=='Cluster': totalsol = indiv.copy() nat = len(totalsol) if debug: logger.info('Extending cluster with {0} atoms to center of evaluation box of size {1}'.format(nat,Optimizer.large_box_size)) origcell = indiv.get_cell() totalsol.set_cell([Optimizer.large_box_size,Optimizer.large_box_size,Optimizer.large_box_size]) totalsol.translate([Optimizer.large_box_size/2.0,Optimizer.large_box_size/2.0,Optimizer.large_box_size/2.0]) elif Optimizer.structure=='Crystal': totalsol = indiv.copy() nat = len(totalsol) else: print 'WARNING: In EvalEnergy. Optimizer.structure not recognized' logger.warning('Optimizer.structure not recognized') # Check for atoms that are too close or out of constrained location if Optimizer.constrain_position: if Optimizer.structure=='Defect': if debug: logger.info('Constraining positions of defect') totalsol, stro = constrain_positions(totalsol, Optimizer.solidbulk, Optimizer.sf) if debug: logger.info(stro) STR+=str0 min_len=0.7 if not Optimizer.fixed_region: if debug: logger.info('Running check minimum distance') totalsol, STR = check_min_dist(totalsol, Optimizer.structure, nat, min_len, STR) if debug: write_xyz(Optimizer.debugfile,totalsol,'After minlength check') Optimizer.debugfile.flush() logger.debug('Writing individual after checking minimum length') # Set calculator to use to get forces/energies if Optimizer.parallel: calc = setup_calculator(Optimizer) if Optimizer.fixed_region: if debug: logger.info('Setting up fixed region calculator') pms=copy.deepcopy(calc.parameters) try: pms['mass'][len(pms['mass'])-1] += '\ngroup RO id >= {0}\nfix freeze RO setforce 0.0 0.0 0.0\n'.format(nat) except KeyError: pms['pair_coeff'][0] += '\ngroup RO id >= {0}\nfix freeze RO setforce 0.0 0.0 0.0\n'.format(nat) calc = LAMMPS(parameters=pms, files=calc.files, keep_tmp_files=calc.keep_tmp_files, tmp_dir=calc.tmp_dir) lmin = copy.copy(Optimizer.lammps_min) if debug: logger.info('Setting up no local minimization calculator') Optimizer.lammps_min = None Optimizer.static_calc = setup_calculator(Optimizer) Optimizer.lammps_min = lmin else: calc=Optimizer.calc totalsol.set_calculator(calc) totalsol.set_pbc(True) # Perform Energy Minimization if not Optimizer.parallel: if debug: write_xyz(Optimizer.debugfile,totalsol,'Individual sent to Energy Minimizer') logger.debug('Writing structure sent to energy minimizer') try: cwd = os.getcwd() if Optimizer.ase_min == True: if debug: logger.info('Running ASE minimizer') if Optimizer.calc_method=='LennardJones': logger.warn('Must run ase LJ calculator with pbc=False') totalsol.set_pbc(False) totalsol, energy, pressure, volume, STR = run_ase_min(totalsol, Optimizer.ase_min_fmax, Optimizer.ase_min_maxsteps, Optimizer.fitness_scheme, STR) else: if debug: logger.info('Running local energy calculator') if Optimizer.fixed_region: totalsol, energy, pressure, volume, STR = run_energy_eval(totalsol, Optimizer.calc_method, Optimizer.fixed_region, Optimizer.fitness_scheme, STR, Optimizer.static_calc) else: totalsol, energy, pressure, volume, STR = run_energy_eval(totalsol, Optimizer.calc_method, False, Optimizer.fitness_scheme, STR) except Exception, e: logger.critical('Error in energy evaluation: {0}'.format(e), exc_info=True) path = os.path.join(cwd,'TroubledLammps') if not os.path.exists(path): os.mkdir(path) #Copy files over shutil.copyfile(calc.trajfile,os.path.join(path,os.path.basename(calc.trajfile))) shutil.copyfile(calc.infile,os.path.join(path,os.path.basename(calc.infile))) shutil.copyfile(calc.logfile,os.path.join(path,os.path.basename(calc.logfile))) shutil.copyfile(calc.datafile,os.path.join(path,os.path.basename(calc.datafile))) raise RuntimeError('{0}:{1}'.format(Exception,e)) if not Optimizer.parallel: if debug: write_xyz(Optimizer.debugfile,totalsol,'Individual after Energy Minimization') Optimizer.debugfile.flush() logger.debug('Writing structure recieved from energy minimizer') # Separate structures into distinct pieces if Optimizer.structure=='Defect': if Optimizer.fixed_region==True or Optimizer.finddefects==False: if debug: logger.info('Identifying atoms in defect structure based on ID') individ[0]=totalsol[0:nat] bul=totalsol[(nat):len(totalsol)] individ[0].set_cell(csize) else: if debug: logger.info('Applying find defects scheme to identify R1 and R2 for Defect') if 'FD' in Optimizer.debug: outt=find_defects(totalsol,Optimizer.solidbulk,Optimizer.sf,atomlistcheck=Optimizer.atomlist,trackvacs=Optimizer.trackvacs,trackswaps=Optimizer.trackswaps,debug=Optimizer.debugfile) else: outt=find_defects(totalsol,Optimizer.solidbulk,Optimizer.sf,atomlistcheck=Optimizer.atomlist,trackvacs=Optimizer.trackvacs,trackswaps=Optimizer.trackswaps,debug=False) individ[0]=outt[0] bul=outt[1] individ.vacancies = outt[2] individ.swaps = outt[3] STR += outt[4] indiv=individ[0] elif Optimizer.structure=='Surface': if debug: logger.info('Finding surface top layer') top,bul=find_top_layer(totalsol,Optimizer.surftopthick) indiv=top.copy() individ[0]=top.copy() bul = Atoms() elif Optimizer.structure=='Crystal': if debug: logger.info('Checking crystal cell type') celltype = check_cell_type(totalsol) STR+='Cell structure = {0}\n'.format(celltype) bul = Atoms() individ[0] = totalsol.copy() elif Optimizer.structure=='Cluster': volume = get_cluster_volume(totalsol) bul = Atoms() if debug: logger.info('Translating cluster back to smaller box size location') totalsol.translate([-Optimizer.large_box_size/2.0,-Optimizer.large_box_size/2.0,-Optimizer.large_box_size/2.0]) totalsol.set_cell(origcell) individ[0] = totalsol.copy() # Add concentration energy dependence if Optimizer.forcing=='energy_bias': if debug: logger.info('Applying energy bias for atoms with different number of atoms of type than in atomlist') n=[0]*len(Optimizer.atomlist) for i in range(len(Optimizer.atomlist)): n[i]=len([inds for inds in totalsol if inds.symbol==Optimizer.atomlist[i][0]]) n[i]=abs(n[i]-Optimizer.atomlist[i][1]) factor=sum(n)**3 energy=(energy+factor)/totalsol.get_number_of_atoms() STR+='Energy with Bias = {0}\n'.format(energy) elif Optimizer.forcing=='chem_pot': if debug: logger.info('Applying chemical potential bias for atoms with different number of atoms of type than in atomlist') n=[0]*len(Optimizer.atomlist) for i in range(len(Optimizer.atomlist)): n[i]=len([inds for inds in totalsol if inds.symbol==Optimizer.atomlist[i][0]]) n[i]=n[i]*Optimizer.atomlist[i][3] factor=sum(n) energy=(energy+factor)/totalsol.get_number_of_atoms() STR+='Energy with Chemical Potential = {0}\n'.format(energy) individ.energy=energy individ.buli=bul individ.pressure=pressure individ.volume=volume if Optimizer.fingerprinting: if debug: logger.info('Identifying fingerprint of new structure') individ.fingerprint=get_fingerprint(Optimizer,individ,Optimizer.fpbin,Optimizer.fpcutoff) if Optimizer.parallel: calc.clean() signal = 'Evaluated individual {0} on {1}\n'.format(individ.index,rank) signal +=STR else: signal=STR
def get_defect_indiv_random(Optimizer): """ Function to generate a structopt Individual class structure with a defect structure. Inputs: Optimizer = structopt Optimizer class object Outputs: individ = structopt Individual class object containing defect structure data """ #Initialize Bulk - Generate or load positions of bulk solid if not Optimizer.solidbulk: if 'Island_Method' not in Optimizer.algorithm_type: outfilename = os.path.join(os.path.join(os.getcwd(),Optimizer.filename),'Bulkfile.xyz') else: from mpi4py import MPI rank = MPI.COMM_WORLD.Get_rank() outfilename = os.path.join(os.path.join(os.getcwd(),Optimizer.filename+'-rank'+repr(rank)),'Bulkfile.xyz') if Optimizer.evalsolid: if Optimizer.parallel: from MAST.structopt.tools.setup_calculator import setup_calculator Optimizer.calc = setup_calculator(Optimizer) bulk1, PureBulkEnpa, stro = gen_solid(Optimizer.solidfile, Optimizer.solidcell,outfilename,Optimizer.calc,Optimizer.calc_method) Optimizer.output.write(stro) else: bulk1 = gen_solid(Optimizer.solidfile,Optimizer.solidcell,outfilename) PureBulkEnpa = 0 natomsbulk = len(bulk1) Optimizer.solidbulk = bulk1.copy() Optimizer.purebulkenpa = PureBulkEnpa Optimizer.natomsbulk = natomsbulk # Identify nearby atoms for region 2 inclusion bulk = Optimizer.solidbulk.copy() bulkcom = bulk.get_center_of_mass() bulk.translate(-bulkcom) if Optimizer.sf != 0: bulk.append(Atom(position=[0,0,0])) nbulk = Atoms(pbc=True, cell=bulk.get_cell()) nr2 = Atoms(pbc=True, cell=bulk.get_cell()) for i in range(len(bulk)-1): dist = bulk.get_distance(-1,i) if dist <= Optimizer.sf: nr2.append(bulk[i]) else: nbulk.append(bulk[i]) else: nbulk = bulk.copy() nr2 = Atoms(pbc=True, cell=bulk.get_cell()) #Update atom list with atoms in region 2 natlist = [] for sym,c,m,u in Optimizer.atomlist: atsym = [atm for atm in nr2 if atm.symbol==sym] natlist.append((sym,len(atsym),m,u)) # Generate random individual and region 2 if 'sphere' in Optimizer.generate_flag: ind = gen_pop_sphere(Optimizer.atomlist,Optimizer.size) elif 'dumbbell' in Optimizer.generate_flag: ind = Atoms(cell=[Optimizer.size for i in range(3)], pbc=True) for sym,c,m,u in Optimizer.atomlist: if c > 0: dums = generate_dumbbells(c, dumbbellsym=sym, nindiv=1, solid = Optimizer.solidbulk, size=Optimizer.size)[0] ind.extend(dums) else: ind = gen_pop_box(Optimizer.atomlist,Optimizer.size) nnr2 = gen_pop_sphere(natlist, Optimizer.sf*2.0) nnr2.translate([-Optimizer.sf,-Optimizer.sf,-Optimizer.sf]) nnr2.set_pbc(True) nnr2.set_cell(bulk.get_cell()) # Initialize class individual with known values individ = Individual(ind) individ.purebulkenpa = Optimizer.purebulkenpa individ.natomsbulk = Optimizer.natomsbulk # Combine individual with R2 icom = ind.get_center_of_mass() ind.translate(-icom) ind.extend(nnr2) ind.set_pbc(True) ind.set_cell(bulk.get_cell()) # Recenter structure nbulk.translate(bulkcom) ind.translate(bulkcom) individ[0] = ind.copy() individ.bulki = nbulk.copy() individ.bulko = nbulk.copy() bulk = nbulk.copy() bul = bulk.copy() for atm in individ[0]: bul.append(atm) indices = [] for sym,c,m,u in Optimizer.atomlist: if c < 0: if Optimizer.randvacst: alist = [one for one in bul if one.symbol==sym] count = abs(c) while count > 0: indices.append(random.choice(alist).index) count -= 1 else: pos = individ[0][0:Optimizer.natoms].get_center_of_mass() count = abs(c) bul.append(Atom(position=pos)) alist = [one for one in bul if one.symbol==sym] alistd = [(bul.get_distance(len(bul)-1,one.index),one.index) for one in alist] alistd.sort(reverse=True) bul.pop() while count > 0: idx = alistd.pop()[1] indices.append(idx) count-=1 if len(indices) !=0: nbulklist = [at for at in bul if at.index not in indices and at.index<len(bulk)] nalist = [at for at in bul if at.index not in indices and at.index>=len(bulk)] bulkn = Atoms(cell=bulk.get_cell(),pbc=True) for atm in nbulklist: bulkn.append(atm) individ.bulki = bulkn.copy() individ.bulko = bulkn.copy() newind = Atoms() for atm in nalist: newind.append(atm) newind.set_cell(individ[0].get_cell()) newind.set_pbc(True) individ[0] = newind return individ
def eval_energy(input): """Function to evaluate energy of an individual Inputs: input = [Optimizer class object with parameters, Individual class structure to be evaluated] Outputs: energy, bul, individ, signal energy = energy of Individual evaluated bul = bulk structure of Individual if simulation structure is Defect individ = Individual class structure evaluated signal = string of information about evaluation """ if input[0]==None: energy=0 bul=0 individ=0 rank = MPI.COMM_WORLD.Get_rank() signal='Evaluated none individual on '+repr(rank)+'\n' else: [Optimizer, individ]=input if Optimizer.calc_method=='MAST': energy = individ.energy bul = individ.energy signal = 'Recieved MAST structure\n' else: if Optimizer.parallel: rank = MPI.COMM_WORLD.Get_rank() if not Optimizer.genealogy: STR='----Individual ' + str(individ.index)+ ' Optimization----\n' else: STR='----Individual ' + str(individ.history_index)+ ' Optimization----\n' indiv=individ[0] if 'EE' in Optimizer.debug: debug = True else: debug = False if debug: write_xyz(Optimizer.debugfile,indiv,'Recieved by eval_energy') Optimizer.debugfile.flush() if Optimizer.structure=='Defect': indi=indiv.copy() if Optimizer.alloy==True: bulk=individ.bulki else: bulk=individ.bulko nat=indi.get_number_of_atoms() csize=bulk.get_cell() totalsol=Atoms(cell=csize, pbc=True) totalsol.extend(indi) totalsol.extend(bulk) for sym,c,m,u in Optimizer.atomlist: nc=len([atm for atm in totalsol if atm.symbol==sym]) STR+='Defect configuration contains '+repr(nc)+' '+repr(sym)+' atoms\n' elif Optimizer.structure=='Surface': totalsol=Atoms() totalsol.extend(indiv) nat=indiv.get_number_of_atoms() totalsol.extend(individ.bulki) for sym,c,m,u in Optimizer.atomlist: nc=len([atm for atm in totalsol if atm.symbol==sym]) STR+='Surface-Bulk configuration contains '+repr(nc)+' '+repr(sym)+' atoms\n' cell=numpy.maximum.reduce(indiv.get_cell()) totalsol.set_cell([cell[0],cell[1],500]) totalsol.set_pbc([True,True,False]) if Optimizer.constrain_position: ts = totalsol.copy() indc,indb,vacant,swap,stro = find_defects(ts,Optimizer.solidbulk,0) sbulk = Optimizer.solidbulk.copy() bcom = sbulk.get_center_of_mass() #totalsol.translate(-bulkcom) #indc.translate(-bulkcom) #totalsol.append(Atom(position=[0,0,0])) # for one in indc: # index = [atm.index for atm in totalsol if atm.position[0]==one.position[0] and atm.position[1]==one.position[1] and atm.position[2]==one.position[2]][0] # if totalsol.get_distance(-1,index) > Optimizer.sf: # r = random.random() # totalsol.set_distance(-1,index,Optimizer.sf*r,fix=0) # totalsol.pop() # totalsol.translate(bulkcom) com = indc.get_center_of_mass() dist = (sum((bcom[i] - com[i])**2 for i in range(3)))**0.5 if dist > Optimizer.sf: STR+='Shifting structure to within region\n' r = random.random()*Optimizer.sf comv = numpy.linalg.norm(com) ncom = [one*r/comv for one in com] trans = [ncom[i]-com[i] for i in range(3)] indices = [] for one in indc: id = [atm.index for atm in totalsol if atm.position[0]==one.position[0] and atm.position[1]==one.position[1] and atm.position[2]==one.position[2]][0] totalsol[id].position += trans # Check for atoms that are too close min_len=0.7 #pdb.set_trace() if not Optimizer.fixed_region: if Optimizer.structure=='Defect' or Optimizer.structure=='Surface': cutoffs=[2.0 for one in totalsol] nl=NeighborList(cutoffs,bothways=True,self_interaction=False) nl.update(totalsol) for one in totalsol[0:nat]: nbatoms=Atoms() nbatoms.append(one) indices, offsets=nl.get_neighbors(one.index) for index, d in zip(indices,offsets): index = int(index) sym=totalsol[index].symbol pos=totalsol[index].position + numpy.dot(d,totalsol.get_cell()) at=Atom(symbol=sym,position=pos) nbatoms.append(at) while True: dflag=False for i in range(1,len(nbatoms)): d=nbatoms.get_distance(0,i) if d < min_len: nbatoms.set_distance(0,i,min_len+.01,fix=0.5) STR+='--- WARNING: Atoms too close (<0.7A) - Implement Move ---\n' dflag=True if dflag==False: break for i in range(len(indices)): totalsol[indices[i]].position=nbatoms[i+1].position totalsol[one.index].position=nbatoms[0].position nl.update(totalsol) if debug: write_xyz(Optimizer.debugfile,totalsol,'After minlength check') Optimizer.debugfile.flush() else: for i in range(len(indiv)): for j in range(len(indiv)): if i != j: d=indiv.get_distance(i,j) if d < min_len: indiv.set_distance(i,j,min_len,fix=0.5) STR+='--- WARNING: Atoms too close (<0.7A) - Implement Move ---\n' if debug: write_xyz(Optimizer.debugfile,indiv,'After minlength check') Optimizer.debugfile.flush() # Set calculator to use to get forces/energies if Optimizer.parallel: calc = setup_calculator(Optimizer) if Optimizer.fixed_region: pms=copy.deepcopy(calc.parameters) try: pms['mass'][len(pms['mass'])-1] += '\ngroup RO id >= '+repr(nat)+'\nfix freeze RO setforce 0.0 0.0 0.0\n' except KeyError: pms['pair_coeff'][0] += '\ngroup RO id >= '+repr(nat)+'\nfix freeze RO setforce 0.0 0.0 0.0\n' calc = LAMMPS(parameters=pms, files=calc.files, keep_tmp_files=calc.keep_tmp_files, tmp_dir=calc.tmp_dir) lmin = copy.copy(Optimizer.lammps_min) Optimizer.lammps_min = None Optimizer.static_calc = setup_calculator(Optimizer) Optimizer.lammps_min = lmin else: calc=Optimizer.calc if Optimizer.structure=='Defect' or Optimizer.structure=='Surface': totalsol.set_calculator(calc) totalsol.set_pbc(True) else: indiv.set_calculator(calc) indiv.set_pbc(True) #Current bug in ASE optimizer-Lammps prevents pbc=false if Optimizer.structure=='Cluster': indiv.set_cell([500,500,500]) indiv.translate([250,250,250]) cwd=os.getcwd() # Perform Energy Minimization if not Optimizer.parallel: Optimizer.output.flush() if Optimizer.ase_min == True: try: if Optimizer.structure=='Defect' or Optimizer.structure=='Surface': dyn=BFGS(totalsol) else: dyn=BFGS(indiv) dyn.run(fmax=Optimizer.ase_min_fmax, steps=Optimizer.ase_min_maxsteps) except OverflowError: STR+='--- Error: Infinite Energy Calculated - Implement Random ---\n' box=Atoms() indiv=gen_pop_box(Optimizer.natoms, Optimizer.atomlist, Optimizer.size) indiv.set_calculator(calc) dyn=BFGS(indiv) dyn.run(fmax=fmax, steps=steps) except numpy.linalg.linalg.LinAlgError: STR+='--- Error: Singular Matrix - Implement Random ---\n' indiv=gen_pop_box(Optimizer.natoms, Optimizer.atomlist, Optimizer.size) indiv.set_calculator(calc) dyn=BFGS(indiv) dyn.run(fmax=fmax, steps=steps) # Get Energy of Minimized Structure if Optimizer.structure=='Defect' or Optimizer.structure=='Surface': en=totalsol.get_potential_energy() #force=numpy.maximum.reduce(abs(totalsol.get_forces())) if Optimizer.fitness_scheme == 'enthalpyfit': pressure=totalsol.get_isotropic_pressure(totalsol.get_stress()) cell_max=numpy.maximum.reduce(totalsol.get_positions()) cell_min=numpy.minimum.reduce(totalsol.get_positions()) cell=cell_max-cell_min volume=cell[0]*cell[1]*cell[2] else: pressure=0 volume=0 na=totalsol.get_number_of_atoms() ena=en/na energy=en individ[0]=totalsol[0:nat] bul=totalsol[(nat):len(totalsol)] STR+='Number of positions = '+repr(len(bul)+len(individ[0]))+'\n' individ[0].set_cell(csize) indiv=individ[0] else: en=indiv.get_potential_energy() if Optimizer.fitness_scheme == 'enthalpyfit': pressure=indiv.get_isotropic_pressure(indiv.get_stress()) cell_max=numpy.maximum.reduce(indiv.get_positions()) cell_min=numpy.minimum.reduce(indiv.get_positions()) cell=cell_max-cell_min volume=cell[0]*cell[1]*cell[2] else: pressure=0 volume=0 na=indiv.get_number_of_atoms() ena=en/na energy=ena individ[0]=indiv bul=0 else: if Optimizer.structure=='Defect' or Optimizer.structure=='Surface': if Optimizer.calc_method=='VASP': en=totalsol.get_potential_energy() calcb=Vasp(restart=True) totalsol=calcb.get_atoms() stress=calcb.read_stress() else: try: totcop=totalsol.copy() if debug: write_xyz(Optimizer.debugfile,totcop,'Individual sent to lammps') OUT=totalsol.calc.calculate(totalsol) totalsol=OUT['atoms'] totalsol.set_pbc(True) if Optimizer.fixed_region: if debug: print 'Energy of fixed region calc = ', OUT['thermo'][-1]['pe'] totalsol.set_calculator(Optimizer.static_calc) OUT=totalsol.calc.calculate(totalsol) totalsol=OUT['atoms'] totalsol.set_pbc(True) if debug: print 'Energy of static calc = ', OUT['thermo'][-1]['pe'] en=OUT['thermo'][-1]['pe'] stress=numpy.array([OUT['thermo'][-1][i] for i in ('pxx','pyy','pzz','pyz','pxz','pxy')])*(-1e-4*GPa) #force=numpy.maximum.reduce(abs(totalsol.get_forces())) if debug: write_xyz(Optimizer.debugfile,totalsol,'After Lammps Minimization') Optimizer.debugfile.flush() except Exception, e: os.chdir(cwd) STR+='WARNING: Exception during energy eval:\n'+repr(e)+'\n' f=open('problem-structures.xyz','a') write_xyz(f,totcop,data='Starting structure hindex='+individ.history_index) write_xyz(f,totalsol,data='Lammps Min structure') en=10 stress=0 f.close() if Optimizer.fitness_scheme == 'enthalpyfit': pressure=totalsol.get_isotropic_pressure(stress) cell_max=numpy.maximum.reduce(totalsol.get_positions()) cell_min=numpy.minimum.reduce(totalsol.get_positions()) cell=cell_max-cell_min volume=cell[0]*cell[1]*cell[2] else: pressure=totalsol.get_isotropic_pressure(stress) volume=0 na=totalsol.get_number_of_atoms() ena=en/na energy=en if Optimizer.structure=='Defect': if Optimizer.fixed_region==True or Optimizer.finddefects==False: individ[0]=totalsol[0:nat] bul=totalsol[(nat):len(totalsol)] individ[0].set_cell(csize) else: if 'FI' in Optimizer.debug: outt=find_defects(totalsol,Optimizer.solidbulk,Optimizer.sf,atomlistcheck=Optimizer.atomlist,trackvacs=Optimizer.trackvacs,trackswaps=Optimizer.trackswaps,debug=Optimizer.debugfile) else: outt=find_defects(totalsol,Optimizer.solidbulk,Optimizer.sf,atomlistcheck=Optimizer.atomlist,trackvacs=Optimizer.trackvacs,trackswaps=Optimizer.trackswaps,debug=False) individ[0]=outt[0] bul=outt[1] individ.vacancies = outt[2] individ.swaps = outt[3] STR += outt[4] indiv=individ[0] else: top,bul=find_top_layer(totalsol,Optimizer.surftopthick) indiv=top.copy() individ[0]=top.copy() else: