def get_energy_diff_by_spacegroup(ase_atoms_list, target='energy_total', equiv_spgroups=None): logging.debug("Using {} as target.".format(target)) chemical_formula_list = [] energy_list = [] label_list = [] for idx_atoms, ase_atoms in enumerate(ase_atoms_list): energy = ase_atoms.info[target] # get chemical_formula, energy, classification (space group) for binaires label = get_spacegroup(ase_atoms).no # chemical_formula = list(set(ase_atoms.get_chemical_symbols())) chemical_formula = ase_atoms.get_chemical_formula(mode='hill') chemical_formula_list.append(chemical_formula) label_list.append(label) energy_list.append(energy) # the last iteration calculate the energy differences between space group with all the json_file data dict_delta_e = get_binaries_dict_delta_e(chemical_formula_list, energy_list, label_list, equiv_spgroups=equiv_spgroups) return dict_delta_e
def prebeta_spacegroup(n_template_structs=0): atoms = bulk("Al", cubic=True) # Add one site at the center L = atoms.get_cell()[0,0] at = Atoms( "X", positions=[[L/2,L/2,L/2]] ) atoms.extend(at) view(atoms) sp_gr = get_spacegroup(atoms) print(sp_gr) print(atoms.get_scaled_positions()) sc = atoms*(6,6,6) jump_moves = CollectiveJumpMove(mc_cell=sc) jump_moves.view_columns() temp_atoms = atoms*(2,2,2) print(len(temp_atoms)) view(temp_atoms) if n_template_structs > 0: symbs = ["Al","Mg","Si"] for i in range(n_template_structs): atoms = bulk("Al",cubic=True,a=4.05) selection = [symbs[randint(low=0,high=3)] for _ in range(len(atoms))] for indx in range(len(atoms)): atoms[indx].symbol = selection[indx] at = Atoms( "X", positions=[[L/2,L/2,L/2]] ) atoms.extend(at) atoms = atoms*(2,2,2) fname = "data/prebeta_template{}.xyz".format(i) write(fname,atoms) print("Template structure written to {}".format(fname))
def get_spgroup(argv): """Get spacegroup from list of files""" #------------------------------------------------------------------------------- # Argument parser #------------------------------------------------------------------------------- parser = argparse.ArgumentParser(description=__doc__) # Optional args parser.add_argument('-f', '--files', dest="filenames", default=["POSCAR", "CONTCAR"], type=str, nargs='+', help='geometry files. Default POSCAR, CONTCAR;') parser.add_argument('--symprec', dest='symprec', type=float, default=1e-5, help='set precision on symmetry operations.') parser.add_argument('--debug', action='store_true', dest='debug', help='show debug informations.') #------------------------------------------------------------------------------- # Initialize and check variables #------------------------------------------------------------------------------- args = parser.parse_args(argv) # Set up LOGGER c_log = logging.getLogger(__name__) # Adopted format: level - current function name - mess. Width is fixed as visual aid std_format = '[%(levelname)5s - %(funcName)10s] %(message)s' logging.basicConfig(format=std_format) c_log.setLevel(logging.INFO) # Set debug option if args.debug: c_log.setLevel(logging.DEBUG) c_log.debug(args) #------------------------------------------------------------------------------- # Load geometry and print in cartesian #------------------------------------------------------------------------------- spgroups = [ get_spacegroup(read(filename), symprec=args.symprec) for filename in args.filenames ] for f, spg in zip(args.filenames, spgroups): print("Geom %s Spacegroup symbol %s (%i)" % (f, spg.symbol, spg.no)) return spgroups
def misfit_strain(): from ase.spacegroup import get_spacegroup mgsi100 = read("data/mgsi100_fully_relaxed.xyz") print(get_spacegroup(mgsi100, symprec=1E-4)) atoms = bulk("Al") * (2, 2, 2) cell_mgsi = mgsi100.get_cell().T cell_al = atoms.get_cell().T F = cell_mgsi.dot(np.linalg.inv(cell_al)) eps = 0.5 * (F.T.dot(F) - np.eye(3)) print(eps) print(np.linalg.eigvals(eps))
def misfit_strain(): from ase.spacegroup import get_spacegroup mgsi_interstitial = read("data/mgsi_interstitial_fully_relaxed.xyz") print(get_spacegroup(mgsi_interstitial, symprec=1E-4)) atoms = bulk("Al", crystalstructure="sc", cubic=True, a=2.025)*(4, 4, 2) cell_mgsi = mgsi_interstitial.get_cell().T cell_al = atoms.get_cell().T F = cell_mgsi.dot(np.linalg.inv(cell_al)) eps = 0.5*(F.T.dot(F) - np.eye(3)) print(eps) print(np.linalg.eigvals(eps))
def rotate_and_translate(atoms, atoms_index_group1, translation, rotation_x, rotation_y, rotation_z): """ atoms: atoms class in ASE module atoms_group1: atoms index that belong to molecule1 return a new structure that has a,b,c,alpha,beta,gamma perturbed and the center of mass of asymmetric unit to the origin changed """ # get all scaled_positions space_group = spacegroup.get_spacegroup(atoms) scaled_positions = atoms.get_scaled_positions() #atoms_group1 = scaled_positions[::4] atoms_group1 = [] #for i in range(1, atoms.get_number_of_atoms()): # if atom_belong_to_mol1(i, atoms): # atoms_group1.append(scaled_positions[i-1]) # print("dir(atom): ", dir(atoms[1])) #print("atoms[0].scaled_position: ",atoms[0]) #atoms_group1.append(atoms[i].get("scaled_position")) #print("atoms_group1_old: ", scaled_positions[::4]) #print("atoms_group1_new: ", np.array(atoms_group1)) for i in atoms_index_group1: atoms_group1.append(scaled_positions[i - 1]) # apply a translation to atoms_group_1 atoms_group1_translate = np.add(atoms_group1, translation) atoms_group1_rotation = np.dot(atoms_group1_translate, rotation_x) atoms_group1_rotation = np.dot(atoms_group1_translate, rotation_y) atoms_group1_rotation = np.dot(atoms_group1_translate, rotation_z) new_arr = [] for row in atoms_group1_rotation: new_row = [] for pos in row: if pos >= 1: pos = pos - 1 elif pos < 0: pos = pos + 1 new_row.append(pos) new_arr.append(new_row) atoms_group1_updated = np.array(new_arr) atoms_scaled_final = get_equivalent_sites(atoms_group1_updated, space_group) return atoms_scaled_final
def main(): args = parse_args() print("args", args) if args.implementation == TORCHANI: from torchani_calculator import torchani_calculator calculator = torchani_calculator(args.network_type) elif args.implementation == AES_ANI: from ani_ase import ani_ase_calculator calculator = ani_ase_calculator(args.network_type) elif args.implementation == KHAN: from khan_calculator import khan_calculator calculator = khan_calculator(args.network_type, args.khan_network, args.numb_networks) assert args.cif_file.endswith('.cif') atoms = ase_io.read(args.cif_file) print("Space group of crystal: %s" % spacegroup.get_spacegroup(atoms)) print("initial unit cell") print(atoms.cell) atom_index_group1 = [] for i in range(1, atoms.get_number_of_atoms()): if atom_belong_to_mol1(i, atoms): atom_index_group1.append(i) MC_steps = int(args.MC) all_frames = 'all_frames.xyz' for i in range(0, int(MC_steps)): atoms.set_calculator(calculator) old_frame = atoms.copy() old_frame.set_calculator(calculator) new_frame, message = Monte_Carlo(old_frame, atom_index_group1, calculator) print("MC step %d" % i) if message == 'Accepted': outfile = "Accepted_%d.cif" % i ase_io.write(all_frames, atoms, append=True) ase_io.write(outfile, atoms) atoms = new_frame.copy()
def read_atomic_structures(data_folder, nb_max_folders=1000, nb_max_files=10000, filename_suffix='.aims', format_input='aims', calc_spgroup=False, symprec=(1e-03, 1e-06, 1e-09)): """Read geometry files from data_folder, and return ASE list""" ase_atoms_list = [] i = 0 j = 0 for root, dirs, files in os.walk(data_folder): i += 1 if i > nb_max_folders: # this is for folders break for file_ in files: j += 1 if j > nb_max_files: # this is for files i = nb_max_folders + 1 break if file_.endswith(filename_suffix): filepath = os.path.join(root, file_) filename_no_ext, file_extension = os.path.splitext(filepath) # read only first element atoms = ase.io.read(filepath, index=0, format=format_input) if calc_spgroup: spgroups = [ get_spacegroup(atoms, symprec=item).no for item in symprec ] for idx_spgroup, spgroups in enumerate(spgroups): atoms.info['spacegroup_' + str(symprec[idx_spgroup])] = spgroups ase_atoms_list.append(atoms) return ase_atoms_list
def test_no_throw(self): if (not available): self.skipTest(reason) return no_throw = True msg = "" try: atoms = bulk("Al",cubic=True) # Add one site at the center L = atoms.get_cell()[0,0] at = Atoms( "X", positions=[[L/2,L/2,L/2]] ) atoms.extend(at) sp_gr = get_spacegroup(atoms) sc = atoms*(2,2,2) jump_moves = CollectiveJumpMove(mc_cell=sc) except Exception as exc: msg = str(exc) no_throw = False self.assertTrue(no_throw, msg=msg)
def find_spacegroup(): a = 4.05 c = 6.0 cell = [[2.0 * a, 0, 0], [0.0, np.sqrt(3) * a, 0.0], [0.0, 0.0, c]] hcp_sites = [ [a / 2.0, 0.0, 0.0], [3.0 * a / 2.0, 0.0, 0.0], [0.0, np.sqrt(3.0) * a / 2.0, 0.0], #[2.0*a,np.sqrt(3.0)*a/2.0,0.0], #[a/2.0,np.sqrt(3.0)*a,0.0], #[3.0*a/2.0,np.sqrt(3.0)*a,0.0], [a, np.sqrt(3.0) * a / 2.0, 0.0], [a, a * (0.5 * np.sqrt(3) - 1 / np.sqrt(3.0)), c / 2.0], [a / 2.0, 0.5 * a * (np.sqrt(3) + 1.0 / np.sqrt(3.0)), c / 2.0], [3.0 * a / 2.0, 0.5 * a * (np.sqrt(3) + 1.0 / np.sqrt(3.0)), c / 2.0] ] bcc_sites = [ [0.0, 0.0, 0.0], #[2.0*a,0.0,0.0], #[0.0,np.sqrt(3.0)*a,0.0], #[2.0*a,np.sqrt(3.0)*a,0.0], [a, 0.5 * np.sqrt(3) * a, c / 2.0] ] hcp_symbs = ["V" for _ in range(len(hcp_sites))] bcc_symbs = ["Si" for _ in range(len(bcc_sites))] symbs = hcp_symbs + bcc_symbs sites = hcp_sites + bcc_sites atoms = Atoms(symbs, sites) atoms.set_cell(cell) view(atoms) # Find spacegroup sp = spacegroup.get_spacegroup(atoms) print(sp)
def test_geometry(): """Test the ase.geometry module and ase.build.cut() function.""" import numpy as np from ase.build import cut, bulk, fcc111 from ase.cell import Cell from ase.geometry import get_layers, wrap_positions from ase.spacegroup import crystal, get_spacegroup al = crystal('Al', [(0, 0, 0)], spacegroup=225, cellpar=4.05) # Cut out slab of 5 Al(001) layers al001 = cut(al, nlayers=5) correct_pos = np.array([[0., 0., 0.], [0., 0.5, 0.2], [0.5, 0., 0.2], [0.5, 0.5, 0.], [0., 0., 0.4], [0., 0.5, 0.6], [0.5, 0., 0.6], [0.5, 0.5, 0.4], [0., 0., 0.8], [0.5, 0.5, 0.8]]) assert np.allclose(correct_pos, al001.get_scaled_positions()) # Check layers along 001 tags, levels = get_layers(al001, (0, 0, 1)) assert np.allclose(tags, [0, 1, 1, 0, 2, 3, 3, 2, 4, 4]) assert np.allclose(levels, [0., 2.025, 4.05, 6.075, 8.1]) # Check layers along 101 tags, levels = get_layers(al001, (1, 0, 1)) assert np.allclose(tags, [0, 1, 5, 3, 2, 4, 8, 7, 6, 9]) assert np.allclose(levels, [0.000, 0.752, 1.504, 1.880, 2.256, 2.632, 3.008, 3.384, 4.136, 4.888], atol=0.001) # Check layers along 111 tags, levels = get_layers(al001, (1, 1, 1)) assert np.allclose(tags, [0, 2, 2, 4, 1, 5, 5, 6, 3, 7]) assert np.allclose(levels, [0.000, 1.102, 1.929, 2.205, 2.756, 3.031, 3.858, 4.960], atol=0.001) # Cut out slab of three Al(111) layers al111 = cut(al, (1, -1, 0), (0, 1, -1), nlayers=3) correct_pos = np.array([[0.5, 0., 0.], [0., 0.5, 0.], [0.5, 0.5, 0.], [0., 0., 0.], [1 / 6., 1 / 3., 1 / 3.], [1 / 6., 5 / 6., 1 / 3.], [2 / 3., 5 / 6., 1 / 3.], [2 / 3., 1 / 3., 1 / 3.], [1 / 3., 1 / 6., 2 / 3.], [5 / 6., 1 / 6., 2 / 3.], [5 / 6., 2 / 3., 2 / 3.], [1 / 3., 2 / 3., 2 / 3.]]) assert np.allclose(correct_pos, al111.get_scaled_positions()) # Cut out cell including all corner and edge atoms (non-periodic structure) al = cut(al, extend=1.1) correct_pos = np.array([[0., 0., 0.], [0., 2.025, 2.025], [2.025, 0., 2.025], [2.025, 2.025, 0.], [0., 0., 4.05], [2.025, 2.025, 4.05], [0., 4.05, 0.], [2.025, 4.05, 2.025], [0., 4.05, 4.05], [4.05, 0., 0.], [4.05, 2.025, 2.025], [4.05, 0., 4.05], [4.05, 4.05, 0.], [4.05, 4.05, 4.05]]) assert np.allclose(correct_pos, al.positions) # Create an Ag(111)/Si(111) interface ag = crystal(['Ag'], basis=[(0, 0, 0)], spacegroup=225, cellpar=4.09) si = crystal(['Si'], basis=[(0, 0, 0)], spacegroup=227, cellpar=5.43) try: assert get_spacegroup(ag).no == 225 assert get_spacegroup(si).no == 227 except ImportError: pass ag111 = cut(ag, a=(4, -4, 0), b=(4, 4, -8), nlayers=5) # noqa si111 = cut(si, a=(3, -3, 0), b=(3, 3, -6), nlayers=5) # noqa # # interface = stack(ag111, si111) # assert len(interface) == 1000 # assert np.allclose(interface.positions[::100], # [[ 4.08125 , -2.040625 , -2.040625 ], # [ 8.1625 , 6.121875 , -14.284375 ], # [ 10.211875 , 0.00875 , 2.049375 ], # [ 24.49041667, -4.07833333, -16.32208333], # [ 18.37145833, 14.29020833, -24.48166667], # [ 24.49916667, 12.25541667, -20.39458333], # [ 18.36854167, 16.32791667, -30.60645833], # [ 19.0575 , 0.01166667, 5.45333333], # [ 23.13388889, 6.80888889, 1.36722222], # [ 35.3825 , 5.45333333, -16.31333333]]) # # Test the wrap_positions function. positions = np.array([ [4.0725, -4.0725, -1.3575], [1.3575, -1.3575, -1.3575], [2.715, -2.715, 0.], [4.0725, 1.3575, -1.3575], [0., 0., 0.], [2.715, 2.715, 0.], [6.7875, -1.3575, -1.3575], [5.43, 0., 0.]]) cell = np.array([[5.43, 5.43, 0.0], [5.43, -5.43, 0.0], [0.00, 0.00, 40.0]]) positions += np.array([6.1, -0.1, 10.1]) result_positions = wrap_positions(positions=positions, cell=cell) correct_pos = np.array([ [4.7425, 1.2575, 8.7425], [7.4575, -1.4575, 8.7425], [3.385, 2.615, 10.1], [4.7425, -4.1725, 8.7425], [6.1, -0.1, 10.1], [3.385, -2.815, 10.1], [2.0275, -1.4575, 8.7425], [0.67, -0.1, 10.1]]) assert np.allclose(correct_pos, result_positions) positions = wrap_positions(positions, cell, pbc=[False, True, False]) correct_pos = np.array([ [4.7425, 1.2575, 8.7425], [7.4575, -1.4575, 8.7425], [3.385, 2.615, 10.1], [10.1725, 1.2575, 8.7425], [6.1, -0.1, 10.1], [8.815, 2.615, 10.1], [7.4575, 3.9725, 8.7425], [6.1, 5.33, 10.1]]) assert np.allclose(correct_pos, positions) # Test center away from values 0, 0.5 result_positions = wrap_positions(positions, cell, pbc=[True, True, False], center=0.2) correct_pos = [[4.7425, 1.2575, 8.7425], [2.0275, 3.9725, 8.7425], [3.385, 2.615, 10.1], [-0.6875, 1.2575, 8.7425], [6.1, -0.1, 10.1], [3.385, -2.815, 10.1], [2.0275, -1.4575, 8.7425], [0.67, -0.1, 10.1]] assert np.allclose(correct_pos, result_positions) # Test pretty_translation keyword positions = np.array([ [0, 0, 0], [0, 1, 1], [1, 0, 1], [1, 1, 0.]]) cell = np.diag([2, 2, 2]) result = wrap_positions(positions, cell, pbc=[True, True, True], pretty_translation=True) assert np.max(result) < 1 + 1E-10 assert np.min(result) > -1E-10 result = wrap_positions(positions - 5, cell, pbc=[True, True, True], pretty_translation=True) assert np.max(result) < 1 + 1E-10 result = wrap_positions(positions - 5, cell, pbc=[False, True, True], pretty_translation=True) assert np.max(result[:, 0]) < -3 assert np.max(result[:, 1:]) < 1 + 1E-10 # Get the correct crystal structure from a range of different cells def checkcell(cell, name): cell = Cell.ascell(cell) lat = cell.get_bravais_lattice() assert lat.name == name, (lat.name, name) checkcell(bulk('Al').cell, 'FCC') checkcell(bulk('Fe').cell, 'BCC') checkcell(bulk('Zn').cell, 'HEX') checkcell(fcc111('Au', size=(1, 1, 3), periodic=True).cell, 'HEX') checkcell([[1, 0, 0], [0, 1, 0], [0, 0, 1]], 'CUB') checkcell([[1, 0, 0], [0, 1, 0], [0, 0, 2]], 'TET') checkcell([[1, 0, 0], [0, 2, 0], [0, 0, 3]], 'ORC') checkcell([[1, 0, 0], [0, 2, 0], [0.5, 0, 3]], 'ORCC') checkcell([[1, 0, 0], [0, 2, 0], [0.501, 0, 3]], 'MCL') checkcell([[1, 0, 0], [0.5, 3**0.5 / 2, 0], [0, 0, 3]], 'HEX')
return ret_atoms if __name__ == "__main__": print("runing main function for debugging...") atoms = ase_io.read(sys.argv[1]) spacegroup_number = sys.argv[2] molecule1_atoms_index = molecule_lists(atoms)[0] print(molecule_lists(atoms)) print("molecule1_atoms_index: ", molecule1_atoms_index) if spacegroup_number: space_group = Spacegroup(int(spacegroup_number)) else: space_group = spacegroup.get_spacegroup(atoms) print("before perturbation: ", space_group) # first enlarge cell and then change the anlge. #ret_atoms = ret_atoms_translate.copy() # atoms_input = atoms.copy() # ret_atoms = generate_perturb(atoms_input) # dummy input ret_atoms = Atoms('Au', positions=[[0, 10 / 2, 10 / 2]], cell=[10, 10, 10], pbc=[1, 0, 0]) counter = 1 while (len(molecule_lists(atoms)) != len(molecule_lists(ret_atoms))): print("attemp %d " % counter) counter += 1
def main(): args = parse_args() print("args", args) if args.implementation == TORCHANI: from torchani_calculator import torchani_calculator calculator = torchani_calculator(args.network_type, args.numb_networks) elif args.implementation == AES_ANI: from ani_ase import ani_ase_calculator calculator = ani_ase_calculator(args.network_type) elif args.implementation == KHAN: from khan_calculator import khan_calculator calculator = khan_calculator(args.network_type, args.khan_network, args.numb_networks) #assert args.cif_file.endswith('.cif') or args.cif_file.endswith('.xyz') if args.cif_file.endswith('.mae'): st = next(StructureReader(args.cif_file)) if args.truncate_box: # reduced size box a = 12.0 deletions = [] for mol in st.molecule: rcom = center_of_mass(st, mol.getAtomIndices()) inbox = [abs(x) < a / 2 for x in rcom] if False in [abs(x) < a / 2 for x in rcom]: deletions.extend(mol.getAtomIndices()) st.deleteAtoms(deletions) rd = rawdataset_from_st([st]) ase_molecs = khan_molec_to_ase_atoms(rd.all_Xs) atoms = ase_molecs[0] if args.truncate_box: # hard coded box #a = 22.6868 vecs = [[a, 0.0, 0.0], [0.0, a, 0.0], [0.0, 0.0, a]] atoms.set_cell(vecs) atoms.set_pbc([True, True, True]) print("after set cell", atoms.get_pbc()) if args.cif_file.endswith('.cif'): atoms = ase_io.read(args.cif_file) if args.box_length is not None: atoms.set_cell([ [args.box_length, 0.0, 0.0], [0.0, args.box_length, 0.0], [0.0, 0.0, args.box_length], ]) atoms.set_pbc([True, True, True]) if args.supercell is not None: atoms = build_supercell(atoms, [args.supercell] * 3) periodic = False not in atoms.get_pbc() print("cell") print(atoms.get_cell()) if periodic: #atoms.wrap() space_group = spacegroup.get_spacegroup(atoms) print("Space group of crystal: %s" % space_group) print("initial unit cell") print(atoms.cell) # this shows how to get unique atoms and there equivalents #scaled_positions = atoms.get_scaled_positions() #unique_positions = space_group.unique_sites(scaled_positions) #all_positions, symmetry_map = space_group.equivalent_sites(unique_positions) #symmetry_groups = defaultdict(list) #for igroup, position in zip(symmetry_map, all_positions): # symmetry_groups[igroup].append(position) #print("unique positions") #for xyz in unique_positions: # print(xyz) #for igroup in sorted(symmetry_groups.keys()): # print("positions in symmetry group %d" % igroup) # for xyz in symmetry_groups[igroup]: # print(xyz) torsions = () if args.torsion is not None: torsions = [( float(args.torsion[0]), int(args.torsion[1]), int(args.torsion[2]), int(args.torsion[3]), )] if args.optimize: # cannot optimize cell until we implement a stress tensor energy = optimize_molecule( atoms, calculator, torsions=torsions, thresh=0.05, optimize_cell=args.relax_cell, ) else: start_time = time.time() energy = single_point_energy(atoms, calculator) print("--- %s seconds ---" % (time.time() - start_time)) if args.dynamics: traj = molecular_dynamics(atoms, calculator, total_time=args.total_time, time_step=args.time_step) if args.cif_file.endswith('.mae'): st = next(StructureReader(args.cif_file)) with StructureWriter("md_path.mae") as writer: for m in traj: st0 = st.copy() st0.setXYZ(m.get_positions()) writer.append(st0) else: with open("md_path.xyz", "w") as fout: xyz_lst = [] for atoms in traj: xyz_lst.append("%d\n" % len(atoms)) species = atoms.get_chemical_symbols() carts = atoms.get_positions() for ch, xyz in zip(species, carts): xyz_lst.append("%s %.8f %.8f %.8f" % (ch, xyz[0], xyz[1], xyz[2])) fout.write("\n".join(xyz_lst)) print("energy of cell (au):", energy) if periodic: space_group = spacegroup.get_spacegroup(atoms) print("Final Space group of crystal: %s" % space_group) print("energy of cell/volume (au):", energy / atoms.get_volume()) print("final unit cell") print(atoms.cell) print("Uncertainty %.4f (kcal/mol)" % (calculator.uncertainty(atoms) * 627.509)) if periodic: outfile = os.path.splitext(args.cif_file)[0] + "_optimized.cif" else: outfile = os.path.splitext(args.cif_file)[0] + "_optimized.xyz" ase_io.write(outfile, atoms) print("final structure written to file: %s" % outfile)
[2.025, 2.025, 4.05], [0., 4.05, 0.], [2.025, 4.05, 2.025], [0., 4.05, 4.05], [4.05, 0., 0.], [4.05, 2.025, 2.025], [4.05, 0., 4.05], [4.05, 4.05, 0.], [4.05, 4.05, 4.05]]) assert np.allclose(correct_pos, al.positions) # Create an Ag(111)/Si(111) interface ag = crystal(['Ag'], basis=[(0, 0, 0)], spacegroup=225, cellpar=4.09) si = crystal(['Si'], basis=[(0, 0, 0)], spacegroup=227, cellpar=5.43) try: assert get_spacegroup(ag).no == 225 assert get_spacegroup(si).no == 227 except ImportError: pass ag111 = cut(ag, a=(4, -4, 0), b=(4, 4, -8), nlayers=5) si111 = cut(si, a=(3, -3, 0), b=(3, 3, -6), nlayers=5) # # interface = stack(ag111, si111) # assert len(interface) == 1000 # assert np.allclose(interface.positions[::100], # [[ 4.08125 , -2.040625 , -2.040625 ], # [ 8.1625 , 6.121875 , -14.284375 ], # [ 10.211875 , 0.00875 , 2.049375 ], # [ 24.49041667, -4.07833333, -16.32208333], # [ 18.37145833, 14.29020833, -24.48166667],
def print_spacegroup(self): g = sg.get_spacegroup(self.atoms) print('Space group', g.no, g.symbol)
print('Getting structures from pool directory...') pool_dir = os.listdir(args.pool_path) pool_structure_files = [] for file in pool_dir: pool_structure_files.append(file) os.chdir(args.pool_path) pool_atoms = [None] * 7568 pool_compositions = [None] * 7568 pool_spacegroups = [None] * 7568 for i in range(7568): pool_atoms[i] = read(str(i) + ".cif") pool_compositions[i] = read(str(i) + ".cif").get_chemical_formula() pool_spacegroups[i] = get_spacegroup(read(str(i) + ".cif")).no print('Making predictions...') pool_feature_vectors = soap.create(pool_atoms, n_jobs=1) pool_feature_pd = pd.DataFrame( pool_feature_vectors) #feature pd is the soap descriptors #generate compositional descriptors #df = pd.read_excel('/Users/ziyanzhang/Downloads/dscribe/examples/hv_temp_cif_labels.xlsx') pool_df = pd.DataFrame(pool_compositions, columns=['composition']) gf = Vectorize_Formula() # empty list for storage of features
def nmd_uri_to_ase_atoms_tmp(nmd_uris, get_energy_total=True, calc_spacegroup=True): """Temporary function to build ASE atoms from nmd uri. Will be substituted from the new option in nomad resolve.""" from nomadcore.nomad_query import NomadQuery nomad_query = NomadQuery() ase_atoms_list = [] target_list = [] if get_energy_total: energy_total_list = [] sec_retrieval_energy = { 'section-2': dict( section_name='section_single_configuration_calculation', paths=[ '/section_run/0c/section_single_configuration_calculation/0c' ]) } # for key, section in sec_retrieval.iteritems(): for (key, section) in viewitems(sec_retrieval_energy): # define a default for retrieved keys # so it will not fail if nothing can be retrieved for idx_nmd, nmd in enumerate(nmd_uris): if idx_nmd % 10 == 0: logger.debug('{0}/{1}'.format(idx_nmd + 1, len(nmd_uris))) for path in section['paths']: nmd_dict = nomad_query.resolve(nmd=nmd, path=path, recursive=True) energy_total = nmd_dict['energy_total'] print(nmd) energy_total_list.append(energy_total) sec_retrieval = { 'section-1': { 'section_name': 'section_system', 'paths': [ '/section_run/0c/section_system/0c', '/section_run/0c/section_system/1c' ], 'required_keys_atom_species': [ 'atom_positions', 'atom_species', 'configuration_periodic_dimensions' ], 'required_keys_atom_labels': [ 'atom_positions', 'atom_labels', 'configuration_periodic_dimensions' ] } } # for key, section in sec_retrieval.iteritems(): for (key, section) in viewitems(sec_retrieval): # define a default for retrieved keys # so it will not fail if nothing can be retrieved required_keys = section['required_keys_atom_species'] for idx_nmd, nmd in enumerate(nmd_uris): retrieval_success = False if idx_nmd % 10 == 0: logger.debug('{0}/{1}'.format(idx_nmd + 1, len(nmd_uris))) for path in section['paths']: try: nmd_dict = nomad_query.resolve(nmd=nmd, path=path, recursive=True) except BaseException: nmd_dict = [] # first try with atom species (this is the correct procedure) if all([ required_key in nmd_dict for required_key in section['required_keys_atom_species'] ]): logging.debug( "Using path {} for query-data retrieval".format(path)) retrieval_success = True required_keys = section['required_keys_atom_species'] # logger.debug("Retrieval succedeed: {}".format(retrieval_success)) # logger.debug("Retrieved keys: {}".format(retrieved_keys)) break if not retrieval_success: # try with atom labels (this is not the correct procedure because atom_labels do not have # necessary to be atomic species (e.g. C1, C2) # we need to do this because there was a bug in the Gaussian parser for path in section['paths']: try: nmd_dict = nomad_query.resolve(nmd=nmd, path=path, recursive=True) except BaseException: nmd_dict = [] # first try with atom species (this is the correct procedure) if all([ required_key in nmd_dict for required_key in section['required_keys_atom_labels'] ]): logging.debug( "Using path {} for query-data retrieval".format( path)) required_keys = section['required_keys_atom_labels'] # logger.debug("Retrieved keys: {}".format(retrieved_keys)) break if all( [required_key in nmd_dict for required_key in required_keys]): if section['section_name'] == 'section_system': atom_positions = np.array( nmd_dict['atom_positions']['flatData']).reshape( nmd_dict['atom_positions']['shape']) * 1.0E+10 periodicity = np.array( nmd_dict['configuration_periodic_dimensions'][0] ['flatData'], dtype=bool) if required_keys == section['required_keys_atom_species']: atom_species = np.array(nmd_dict['atom_species']) elif required_keys == section['required_keys_atom_labels']: atom_species = np.array( nmd_dict['atom_labels']['flatData']) else: logger.error("No retrieved keys. Stopping.") # read cell only if periodicity is all True # the Gaussian parser for non-periodic systems still the cell (0., 0., 0.) even if there is no cell if np.all(periodicity): try: simulation_cell = np.array( nmd_dict['simulation_cell']['flatData'] ).reshape( nmd_dict['simulation_cell']['shape']) * 1.0E+10 except BaseException: simulation_cell = None else: logger.debug( "Calculation {} is not periodic over three dimensions." .format(nmd)) # create ASE object if np.all(periodicity): atoms = ase.Atoms(symbols=atom_species, positions=atom_positions, cell=simulation_cell, pbc=True) # calculate spacegroup on-the-fly # use spacegroup as target for crystals if calc_spacegroup: try: spgroup_nb = get_spacegroup(atoms, symprec=0.001).no except BaseException: spgroup_nb = None atoms.info['spgroup_nb'] = spgroup_nb atoms.info['target'] = spgroup_nb else: atoms = ase.Atoms(symbols=atom_species, positions=atom_positions, cell=simulation_cell, pbc=False) # calculate pointgroup on-the-fly # use pointgroup as target for molecules from pymatgen if calc_spacegroup: try: point_group_symbol = PointGroupAnalyzer( AseAtomsAdaptor.get_structure(atoms), symprec=0.001).get_point_group_symbol() except BaseException: point_group_symbol = None atoms.info['point_group_symbol'] = point_group_symbol atoms.info['target'] = point_group_symbol # add label atoms.info['nmd_uri'] = nmd atoms.info['nmd_checksum'] = nmd.rsplit('/')[-1] # set label # using NMD uri is better because unique, but it prints more to screen atoms.info['label'] = nmd.rsplit('/')[-1] # atoms.info['label'] = str(idx_nmd) ase_atoms_list.append(atoms) target_list.append(atoms.info['target']) else: pass else: logger.info( "Could not retrieve atom_positions and/or atom_species for entry: {} in paths {}" .format(nmd, section['paths'])) if get_energy_total: assert (len(ase_atoms_list) == len(energy_total_list)) for idx, atoms in enumerate(ase_atoms_list): atoms.info['energy_total'] = energy_total_list[idx] return ase_atoms_list
from ase.build import bulk from ase.spacegroup import crystal from wulffpack import SingleCrystal from ase.visualize import view from ase.spacegroup import get_spacegroup from ase.build import cut gamma1 = 0.33 gamma2 = 0.57 surface_energies = {(0, 0, 1): gamma1, (1, 0, 0): gamma2} prim = bulk('Al', crystalstructure='fcc', cubic=True) prim.symbols[[0, 3]] = 'Mg' prim.symbols[[2, 1]] = 'Si' sg = get_spacegroup(prim) prim_cell = sg.scaled_primitive_cell prim = cut(prim, a=prim_cell[0], b=prim_cell[1], c=prim_cell[2]) from ase.visualize import view view(prim) particle = SingleCrystal(surface_energies, primitive_structure=prim, natoms=1000) view(particle.atoms)