def _get_supercell_phonon(self, ph_in): """Return Phonopy instance of supercell as the primitive.""" ph = Phonopy(ph_in.supercell, supercell_matrix=[1, 1, 1], primitive_matrix="P") fc_shape = ph_in.force_constants.shape if fc_shape[0] == fc_shape[1]: # assume full fc ph.force_constants = ph_in.force_constants.copy() else: ph.force_constants = compact_fc_to_full_fc(ph_in, ph_in.force_constants) if ph_in.nac_params: p2p = ph_in.primitive.p2p_map s2p = ph_in.primitive.s2p_map s2pp = [p2p[i] for i in s2p] born_in = ph_in.nac_params["born"] born = [born_in[i] for i in s2pp] nac_params = { "born": np.array(born, dtype="double", order="C"), "factor": ph_in.nac_params["factor"], "dielectric": ph_in.nac_params["dielectric"].copy(), } ph.nac_params = nac_params return ph
def _get_supercell_phonon(self, ph_in): """Returns Phonopy instance of supercell as the primitive""" ph = Phonopy(ph_in.supercell, supercell_matrix=[1, 1, 1], primitive_matrix='P') fc_shape = ph_in.force_constants.shape if fc_shape[0] == fc_shape[1]: # assume full fc ph.force_constants = ph_in.force_constants.copy() else: ph.force_constants = compact_fc_to_full_fc(ph_in, ph_in.force_constants) if ph_in.nac_params: p2p = ph_in.primitive.p2p_map s2p = ph_in.primitive.s2p_map s2pp = [p2p[i] for i in s2p] born_in = ph_in.nac_params['born'] born = [born_in[i] for i in s2pp] nac_params = { 'born': np.array(born, dtype='double', order='C'), 'factor': ph_in.nac_params['factor'], 'dielectric': ph_in.nac_params['dielectric'].copy() } ph.nac_params = nac_params return ph
def get_phonon(pk, pk_nac): n = load_node(pk) unitcell = phonopy_atoms_from_structure(n.inputs.structure) smat = n.outputs.phonon_setting_info['supercell_matrix'] ph = Phonopy(unitcell, supercell_matrix=smat, primitive_matrix='auto') force_sets = n.outputs.force_sets.get_array('force_sets') dataset = n.outputs.phonon_setting_info['displacement_dataset'] ph.dataset = dataset ph.forces = force_sets ph.nac_params = get_nac_params(pk_nac) return ph
def _get_phonon(ph_in): ph = Phonopy(ph_in.supercell, supercell_matrix=[1, 1, 1]) ph.force_constants = ph_in.force_constants born_elems = { s: ph_in.nac_params['born'][i] for i, s in enumerate(ph_in.primitive.symbols) } born = [born_elems[s] for s in ph_in.supercell.symbols] epsilon = ph_in.nac_params['dielectric'] factors = ph_in.nac_params['factor'] ph.nac_params = {'born': born, 'factor': factors, 'dielectric': epsilon} return ph
def _phonons_allclose(self, ph, fc333): ph333 = Phonopy(ph.unitcell, supercell_matrix=[3, 3, 3], primitive_matrix=ph.primitive_matrix) ph333.force_constants = fc333 ph333.nac_params = ph.nac_params comm_points = self._get_comm_points(ph) ph.run_qpoints(comm_points) ph333.run_qpoints(comm_points) np.testing.assert_allclose(ph.get_qpoints_dict()['frequencies'], ph333.get_qpoints_dict()['frequencies'], atol=1e-5)
def _get_phonon(ph_in): ph = Phonopy(ph_in.supercell, supercell_matrix=[1, 1, 1]) ph.force_constants = ph_in.force_constants born_elems = { s: ph_in.nac_params["born"][i] for i, s in enumerate(ph_in.primitive.symbols) } born = [born_elems[s] for s in ph_in.supercell.symbols] epsilon = ph_in.nac_params["dielectric"] factors = ph_in.nac_params["factor"] ph.nac_params = {"born": born, "factor": factors, "dielectric": epsilon} return ph
def _get_phonon(self): cell = read_vasp(os.path.join(data_dir, "..", "POSCAR_NaCl")) phonon = Phonopy(cell, np.diag([2, 2, 2]), primitive_matrix=[[0, 0.5, 0.5], [0.5, 0, 0.5], [0.5, 0.5, 0]]) filename = os.path.join(data_dir, "..", "FORCE_SETS_NaCl") force_sets = parse_FORCE_SETS(filename=filename) phonon.dataset = force_sets phonon.produce_force_constants() filename_born = os.path.join(data_dir, "..", "BORN_NaCl") nac_params = parse_BORN(phonon.get_primitive(), filename=filename_born) phonon.nac_params = nac_params return phonon
def get_phonopy_instance(structure, phonon_settings_dict, params): from phonopy import Phonopy phonon = Phonopy(phonopy_atoms_from_structure(structure), supercell_matrix=phonon_settings_dict['supercell_matrix'], primitive_matrix='auto', symprec=phonon_settings_dict['symmetry_tolerance']) if 'nac_params' in params: from phonopy.interface.calculator import get_default_physical_units units = get_default_physical_units('vasp') factor = units['nac_factor'] nac_params = { 'born': params['nac_params'].get_array('born_charges'), 'dielectric': params['nac_params'].get_array('epsilon'), 'factor': factor } phonon.nac_params = nac_params return phonon
def bunch_phonons(pks, pk_nac, max_items=None, include_ratio=None, linear_decay=True): nodes = [load_node(pk) for pk in pks] displacements, forces, energies = _extract_dataset_from_db( [n.outputs.force_sets for n in nodes], [n.outputs.phonon_setting_info for n in nodes]) d, f, e, idx = _create_dataset(displacements, forces, energies, max_items, include_ratio, linear_decay=linear_decay) unitcell = phonopy_atoms_from_structure(nodes[0].inputs.structure) smat = nodes[0].outputs.phonon_setting_info['supercell_matrix'] ph = Phonopy(unitcell, supercell_matrix=smat, primitive_matrix='auto') ph.dataset = {'displacements': d, 'forces': f} ph.nac_params = get_nac_params(pk_nac) return ph
def dump_phonopy(pk): n = load_node(pk) unitcell = phonopy_atoms_from_structure(n.inputs.structure) smat = n.outputs.phonon_setting_info['supercell_matrix'] ph = Phonopy(unitcell, smat, primitive_matrix='auto') force_sets = n.outputs.force_sets.get_array('force_sets') dataset = n.outputs.phonon_setting_info['displacement_dataset'] ph.dataset = dataset ph.forces = force_sets if 'nac_params' in n.outputs: borns = n.outputs.nac_params.get_array('born_charges') epsilon = n.outputs.nac_params.get_array('epsilon') nac_params = { 'born': borns, 'factor': 14.399652, 'dielectric': epsilon } ph.nac_params = nac_params # phonopy-params.yaml is written out. ph.save() print("phonopy_params.yaml was made for PK=%d" % pk)
nac_params = parse_BORN(primitive, filename="BORN") # Or it can be of course given by hand as follows: # born = [[[1.08703, 0, 0], # [0, 1.08703, 0], # [0, 0, 1.08703]], # [[-1.08672, 0, 0], # [0, -1.08672, 0], # [0, 0, -1.08672]]] # epsilon = [[2.43533967, 0, 0], # [0, 2.43533967, 0], # [0, 0, 2.43533967]] # factors = 14.400 # nac_params = {'born': born, # 'factor': factors, # 'dielectric': epsilon} phonon.nac_params = nac_params # BAND = 0.0 0.0 0.0 0.5 0.0 0.0 0.5 0.5 0.0 0.0 0.0 0.0 0.5 0.5 0.5 bands = [] append_band(bands, [0.0, 0.0, 0.0], [0.5, 0.0, 0.0]) append_band(bands, [0.5, 0.0, 0.0], [0.5, 0.5, 0.0]) append_band(bands, [0.5, 0.5, 0.0], [0.0, 0.0, 0.0]) append_band(bands, [0.0, 0.0, 0.0], [0.5, 0.5, 0.5]) phonon.set_band_structure(bands) band_dict = phonon.get_band_structure_dict() q_points = band_dict['qpoints'] distances = band_dict['distances'] frequencies = band_dict['frequencies'] eigvecs = band_dict['eigenvectors'] for q_path, d_path, freq_path in zip(q_points, distances, frequencies): for q, d, freq in zip(q_path, d_path, freq_path):
def load_phonopy( filename, structure, dim, symprec=1e-5, primitive_matrix=None, factor=VaspToTHz, symmetrise=True, born=None, write_fc=False, ): """Load phonopy output and return an ``phonopy.Phonopy`` object. Args: filename (str): Path to phonopy output. Can be any of ``FORCE_SETS``, ``FORCE_CONSTANTS``, or ``force_constants.hdf5``. structure (:obj:`~pymatgen.core.structure.Structure`): The unitcell structure. dim (list): The supercell size, as a :obj:`list` of :obj:`float`. symprec (:obj:`float`, optional): The tolerance for determining the crystal symmetry. primitive_matrix (:obj:`list` or :obj:`str`, optional): The transformation matrix from the conventional to primitive cell. Only required when the conventional cell was used as the starting structure. Should be provided as a 3x3 :obj:`list` of :obj:`float`. Alternatively the str 'auto' may be provided. factor (:obj:`float`, optional): The conversion factor for phonon frequency. Defaults to :obj:`phonopy.units.VaspToTHz`. symmetrise (:obj:`bool`, optional): Symmetrise the force constants. Defaults to ``True``. born (:obj:`str`, optional): Path to file containing Born effective charges. Should be in the same format as the file produced by the ``phonopy-vasp-born`` script provided by phonopy. write_fc (:obj:`bool` or :obj:`str`, optional): Write the force constants to disk. If ``True``, a ``FORCE_CONSTANTS`` file will be written. Alternatively, if set to ``"hdf5"``, a ``force_constants.hdf5`` file will be written. Defaults to ``False`` (force constants not written). """ unitcell = get_phonopy_structure(structure) num_atom = unitcell.get_number_of_atoms() num_satom = determinant(dim) * num_atom phonon = Phonopy(unitcell, dim, primitive_matrix=primitive_matrix, factor=factor, symprec=symprec) if "FORCE_CONSTANTS" in filename or ".hdf5" in filename: # if force constants exist, use these to avoid recalculating them if ".hdf5" in filename: fc = file_IO.read_force_constants_hdf5(filename) elif "FORCE_CONSTANTS" in filename: fc = file_IO.parse_FORCE_CONSTANTS(filename=filename) if fc.shape[0] != num_satom: msg = ("\nNumber of atoms in supercell is not consistent with the " "matrix shape of\nforce constants read from {}.\nPlease" "carefully check --dim.") logging.error(msg.format(filename)) sys.exit() phonon.force_constants = fc elif "FORCE_SETS" in filename: # load the force sets from file and calculate force constants fs = file_IO.parse_FORCE_SETS(filename=filename) if fs["natom"] != num_satom: msg = ("\nNumber of atoms in supercell is not consistent with the " "the data in FORCE_SETS\nPlease carefully check --dim.") logging.error(msg.format(filename)) sys.exit() phonon.dataset = fs logging.info("Calculating force constants...") phonon.produce_force_constants() if symmetrise: phonon.symmetrize_force_constants() if born: # load born parameters from a file nac_params = file_IO.parse_BORN(phonon._primitive, symprec=symprec, filename=born) # set the nac unit conversion factor manual, specific to VASP nac_params["factor"] = Hartree * Bohr phonon.nac_params = nac_params if write_fc == "hdf5": file_IO.write_force_constants_to_hdf5(phonon.force_constants) logging.info("Force constants written to force_constants.hdf5.") elif write_fc: file_IO.write_FORCE_CONSTANTS(phonon.force_constants) logging.info("Force constants written to FORCE_CONSTANTS.") return phonon