mirror of https://github.com/phonopy/phonopy.git
Improve interface for getting parameters of NAC
This commit is contained in:
parent
7e0fd74fc5
commit
1ad205d0f5
|
@ -42,9 +42,7 @@ import numpy as np
|
||||||
from phonopy.structure.atoms import PhonopyAtoms as Atoms
|
from phonopy.structure.atoms import PhonopyAtoms as Atoms
|
||||||
from phonopy.structure.atoms import symbol_map, atom_data
|
from phonopy.structure.atoms import symbol_map, atom_data
|
||||||
from phonopy.structure.cells import get_primitive, get_supercell
|
from phonopy.structure.cells import get_primitive, get_supercell
|
||||||
from phonopy.structure.symmetry import (Symmetry, get_site_symmetry,
|
from phonopy.structure.symmetry import Symmetry, symmetrize_borns_and_epsilon
|
||||||
get_pointgroup_operations)
|
|
||||||
from phonopy.harmonic.force_constants import similarity_transformation
|
|
||||||
from phonopy.file_IO import (write_FORCE_SETS, write_force_constants_to_hdf5,
|
from phonopy.file_IO import (write_FORCE_SETS, write_force_constants_to_hdf5,
|
||||||
write_FORCE_CONSTANTS)
|
write_FORCE_CONSTANTS)
|
||||||
|
|
||||||
|
@ -397,51 +395,6 @@ def get_born_OUTCAR(poscar_filename="POSCAR",
|
||||||
symmetrize_tensors=symmetrize_tensors,
|
symmetrize_tensors=symmetrize_tensors,
|
||||||
symprec=symprec)
|
symprec=symprec)
|
||||||
|
|
||||||
def symmetrize_borns_and_epsilon(borns,
|
|
||||||
epsilon,
|
|
||||||
ucell,
|
|
||||||
symprec=1e-5,
|
|
||||||
is_symmetry=True):
|
|
||||||
lattice = ucell.get_cell()
|
|
||||||
positions = ucell.get_scaled_positions()
|
|
||||||
u_sym = Symmetry(ucell, is_symmetry=is_symmetry, symprec=symprec)
|
|
||||||
rotations = u_sym.get_symmetry_operations()['rotations']
|
|
||||||
translations = u_sym.get_symmetry_operations()['translations']
|
|
||||||
ptg_ops = get_pointgroup_operations(rotations)
|
|
||||||
epsilon_ = symmetrize_2nd_rank_tensor(epsilon, ptg_ops, lattice)
|
|
||||||
|
|
||||||
for i, Z in enumerate(borns):
|
|
||||||
site_sym = get_site_symmetry(i,
|
|
||||||
lattice,
|
|
||||||
positions,
|
|
||||||
rotations,
|
|
||||||
translations,
|
|
||||||
symprec)
|
|
||||||
Z = symmetrize_2nd_rank_tensor(Z, site_sym, lattice)
|
|
||||||
|
|
||||||
borns_ = np.zeros_like(borns)
|
|
||||||
for i in range(len(borns)):
|
|
||||||
count = 0
|
|
||||||
for r, t in zip(rotations, translations):
|
|
||||||
count += 1
|
|
||||||
diff = np.dot(positions, r.T) + t - positions[i]
|
|
||||||
diff -= np.rint(diff)
|
|
||||||
dist = np.sqrt(np.sum(np.dot(diff, lattice) ** 2, axis=1))
|
|
||||||
j = np.nonzero(dist < symprec)[0][0]
|
|
||||||
r_cart = similarity_transformation(lattice.T, r)
|
|
||||||
borns_[i] += similarity_transformation(r_cart, borns[j])
|
|
||||||
borns_[i] /= count
|
|
||||||
|
|
||||||
return borns_, epsilon_
|
|
||||||
|
|
||||||
def symmetrize_2nd_rank_tensor(tensor, symmetry_operations, lattice):
|
|
||||||
sym_cart = [similarity_transformation(lattice.T, r)
|
|
||||||
for r in symmetry_operations]
|
|
||||||
sum_tensor = np.zeros_like(tensor)
|
|
||||||
for sym in sym_cart:
|
|
||||||
sum_tensor += similarity_transformation(sym, tensor)
|
|
||||||
return sum_tensor / len(symmetry_operations)
|
|
||||||
|
|
||||||
def _get_indep_borns(ucell,
|
def _get_indep_borns(ucell,
|
||||||
borns,
|
borns,
|
||||||
epsilon,
|
epsilon,
|
||||||
|
|
|
@ -36,6 +36,7 @@ import sys
|
||||||
import numpy as np
|
import numpy as np
|
||||||
import phonopy.structure.spglib as spg
|
import phonopy.structure.spglib as spg
|
||||||
from phonopy.structure.atoms import PhonopyAtoms as Atoms
|
from phonopy.structure.atoms import PhonopyAtoms as Atoms
|
||||||
|
from phonopy.harmonic.force_constants import similarity_transformation
|
||||||
|
|
||||||
class Symmetry(object):
|
class Symmetry(object):
|
||||||
def __init__(self, cell, symprec=1e-5, is_symmetry=True):
|
def __init__(self, cell, symprec=1e-5, is_symmetry=True):
|
||||||
|
@ -110,12 +111,12 @@ class Symmetry(object):
|
||||||
rotations = self._symmetry_operations['rotations']
|
rotations = self._symmetry_operations['rotations']
|
||||||
translations = self._symmetry_operations['translations']
|
translations = self._symmetry_operations['translations']
|
||||||
|
|
||||||
return get_site_symmetry(atom_number,
|
return self._get_site_symmetry(atom_number,
|
||||||
lattice,
|
lattice,
|
||||||
positions,
|
positions,
|
||||||
rotations,
|
rotations,
|
||||||
translations,
|
translations,
|
||||||
self._symprec)
|
self._symprec)
|
||||||
|
|
||||||
def get_symmetry_tolerance(self):
|
def get_symmetry_tolerance(self):
|
||||||
return self._symprec
|
return self._symprec
|
||||||
|
@ -129,6 +130,39 @@ class Symmetry(object):
|
||||||
"""
|
"""
|
||||||
return self._reciprocal_operations
|
return self._reciprocal_operations
|
||||||
|
|
||||||
|
def _get_pointgroup_operations(self, rotations):
|
||||||
|
ptg_ops = []
|
||||||
|
for rot in rotations:
|
||||||
|
is_same = False
|
||||||
|
for tmp_rot in ptg_ops:
|
||||||
|
if (tmp_rot == rot).all():
|
||||||
|
is_same = True
|
||||||
|
break
|
||||||
|
if not is_same:
|
||||||
|
ptg_ops.append(rot)
|
||||||
|
|
||||||
|
return ptg_ops
|
||||||
|
|
||||||
|
def _get_site_symmetry(self,
|
||||||
|
atom_number,
|
||||||
|
lattice,
|
||||||
|
positions,
|
||||||
|
rotations,
|
||||||
|
translations,
|
||||||
|
symprec):
|
||||||
|
pos = positions[atom_number]
|
||||||
|
site_symmetries = []
|
||||||
|
|
||||||
|
for r, t in zip(rotations, translations):
|
||||||
|
rot_pos = np.dot(pos, r.T) + t
|
||||||
|
diff = pos - rot_pos
|
||||||
|
diff -= np.rint(diff)
|
||||||
|
diff = np.dot(diff, lattice)
|
||||||
|
if np.linalg.norm(diff) < symprec:
|
||||||
|
site_symmetries.append(r)
|
||||||
|
|
||||||
|
return np.array(site_symmetries, dtype='intc')
|
||||||
|
|
||||||
def _set_symmetry_dataset(self):
|
def _set_symmetry_dataset(self):
|
||||||
self._dataset = spg.get_symmetry_dataset(self._cell, self._symprec)
|
self._dataset = spg.get_symmetry_dataset(self._cell, self._symprec)
|
||||||
self._symmetry_operations = {
|
self._symmetry_operations = {
|
||||||
|
@ -180,7 +214,7 @@ class Symmetry(object):
|
||||||
|
|
||||||
def _set_pointgroup_operations(self):
|
def _set_pointgroup_operations(self):
|
||||||
rotations = self._symmetry_operations['rotations']
|
rotations = self._symmetry_operations['rotations']
|
||||||
ptg_ops = get_pointgroup_operations(rotations)
|
ptg_ops = self._get_pointgroup_operations(rotations)
|
||||||
reciprocal_rotations = [rot.T for rot in ptg_ops]
|
reciprocal_rotations = [rot.T for rot in ptg_ops]
|
||||||
exist_r_inv = False
|
exist_r_inv = False
|
||||||
for rot in ptg_ops:
|
for rot in ptg_ops:
|
||||||
|
@ -285,34 +319,42 @@ def get_lattice_vector_equivalence(point_symmetry):
|
||||||
|
|
||||||
return equivalence
|
return equivalence
|
||||||
|
|
||||||
def get_site_symmetry(atom_number,
|
def symmetrize_borns_and_epsilon(borns,
|
||||||
lattice,
|
epsilon,
|
||||||
positions,
|
ucell,
|
||||||
rotations,
|
symprec=1e-5,
|
||||||
translations,
|
is_symmetry=True):
|
||||||
symprec):
|
lattice = ucell.get_cell()
|
||||||
pos = positions[atom_number]
|
positions = ucell.get_scaled_positions()
|
||||||
site_symmetries = []
|
u_sym = Symmetry(ucell, is_symmetry=is_symmetry, symprec=symprec)
|
||||||
|
rotations = u_sym.get_symmetry_operations()['rotations']
|
||||||
|
translations = u_sym.get_symmetry_operations()['translations']
|
||||||
|
ptg_ops = u_sym.get_pointgroup_operations()
|
||||||
|
epsilon_ = _symmetrize_2nd_rank_tensor(epsilon, ptg_ops, lattice)
|
||||||
|
|
||||||
for r, t in zip(rotations, translations):
|
for i, Z in enumerate(borns):
|
||||||
rot_pos = np.dot(pos, r.T) + t
|
site_sym = u_sym.get_site_symmetry(i)
|
||||||
diff = pos - rot_pos
|
Z = _symmetrize_2nd_rank_tensor(Z, site_sym, lattice)
|
||||||
diff -= np.rint(diff)
|
|
||||||
diff = np.dot(diff, lattice)
|
|
||||||
if np.linalg.norm(diff) < symprec:
|
|
||||||
site_symmetries.append(r)
|
|
||||||
|
|
||||||
return np.array(site_symmetries, dtype='intc')
|
borns_ = np.zeros_like(borns)
|
||||||
|
for i in range(len(borns)):
|
||||||
|
count = 0
|
||||||
|
for r, t in zip(rotations, translations):
|
||||||
|
count += 1
|
||||||
|
diff = np.dot(positions, r.T) + t - positions[i]
|
||||||
|
diff -= np.rint(diff)
|
||||||
|
dist = np.sqrt(np.sum(np.dot(diff, lattice) ** 2, axis=1))
|
||||||
|
j = np.nonzero(dist < symprec)[0][0]
|
||||||
|
r_cart = similarity_transformation(lattice.T, r)
|
||||||
|
borns_[i] += similarity_transformation(r_cart, borns[j])
|
||||||
|
borns_[i] /= count
|
||||||
|
|
||||||
def get_pointgroup_operations(rotations):
|
return borns_, epsilon_
|
||||||
ptg_ops = []
|
|
||||||
for rot in rotations:
|
|
||||||
is_same = False
|
|
||||||
for tmp_rot in ptg_ops:
|
|
||||||
if (tmp_rot == rot).all():
|
|
||||||
is_same = True
|
|
||||||
break
|
|
||||||
if not is_same:
|
|
||||||
ptg_ops.append(rot)
|
|
||||||
|
|
||||||
return ptg_ops
|
def _symmetrize_2nd_rank_tensor(tensor, symmetry_operations, lattice):
|
||||||
|
sym_cart = [similarity_transformation(lattice.T, r)
|
||||||
|
for r in symmetry_operations]
|
||||||
|
sum_tensor = np.zeros_like(tensor)
|
||||||
|
for sym in sym_cart:
|
||||||
|
sum_tensor += similarity_transformation(sym, tensor)
|
||||||
|
return sum_tensor / len(symmetry_operations)
|
||||||
|
|
|
@ -51,8 +51,8 @@ parser = OptionParser()
|
||||||
parser.set_defaults(num_atoms=None,
|
parser.set_defaults(num_atoms=None,
|
||||||
primitive_axis =None,
|
primitive_axis =None,
|
||||||
supercell_matrix=None,
|
supercell_matrix=None,
|
||||||
symmetrize_tensors=False,
|
symmetrize_tensors=True,
|
||||||
read_vasprunxml=False,
|
read_outcar=False,
|
||||||
symprec=1e-5)
|
symprec=1e-5)
|
||||||
parser.add_option("--dim", dest="supercell_matrix",
|
parser.add_option("--dim", dest="supercell_matrix",
|
||||||
action="store", type="string",
|
action="store", type="string",
|
||||||
|
@ -60,24 +60,25 @@ parser.add_option("--dim", dest="supercell_matrix",
|
||||||
parser.add_option("--pa", "--primitive_axis", dest="primitive_axis",
|
parser.add_option("--pa", "--primitive_axis", dest="primitive_axis",
|
||||||
action="store", type="string",
|
action="store", type="string",
|
||||||
help="Same as PRIMITIVE_AXIS tags")
|
help="Same as PRIMITIVE_AXIS tags")
|
||||||
parser.add_option("--st", "--symmetrize_tensors", dest="symmetrize_tensors",
|
parser.add_option("--nost", "--no_symmetrize_tensors",
|
||||||
action="store_true",
|
dest="symmetrize_tensors",
|
||||||
help="Symmetrize tensors")
|
action="store_false",
|
||||||
|
help="Prevent from symmetrizing tensors")
|
||||||
parser.add_option("--tolerance", dest="symprec", type="float",
|
parser.add_option("--tolerance", dest="symprec", type="float",
|
||||||
help="Symmetry tolerance to search")
|
help="Symmetry tolerance to search")
|
||||||
parser.add_option("--vasprunxml", dest="read_vasprunxml",
|
parser.add_option("--outcar", dest="read_outcar",
|
||||||
action="store_true",
|
action="store_true",
|
||||||
help=("Read vasprun.xml instead of OUTCAR. "
|
help=("Read OUTCAR instead of vasprun.xml. "
|
||||||
"POSCAR is not necessary"))
|
"POSCAR is necessary in this case."))
|
||||||
(options, args) = parser.parse_args()
|
(options, args) = parser.parse_args()
|
||||||
|
|
||||||
if args:
|
if args:
|
||||||
outcar_filename = args[0]
|
outcar_filename = args[0]
|
||||||
else:
|
else:
|
||||||
if options.read_vasprunxml:
|
if options.read_outcar:
|
||||||
outcar_filename = "vasprun.xml"
|
|
||||||
else:
|
|
||||||
outcar_filename = "OUTCAR"
|
outcar_filename = "OUTCAR"
|
||||||
|
else:
|
||||||
|
outcar_filename = "vasprun.xml"
|
||||||
|
|
||||||
if len(args) > 1:
|
if len(args) > 1:
|
||||||
poscar_filename = args[1]
|
poscar_filename = args[1]
|
||||||
|
@ -111,17 +112,17 @@ with warnings.catch_warnings() as w:
|
||||||
warnings.simplefilter("always")
|
warnings.simplefilter("always")
|
||||||
|
|
||||||
try:
|
try:
|
||||||
if options.read_vasprunxml:
|
if options.read_outcar:
|
||||||
borns, epsilon, atom_indices = get_born_vasprunxml(
|
borns, epsilon, atom_indices = get_born_OUTCAR(
|
||||||
filename=outcar_filename,
|
poscar_filename=poscar_filename,
|
||||||
|
outcar_filename=outcar_filename,
|
||||||
primitive_matrix=primitive_axis,
|
primitive_matrix=primitive_axis,
|
||||||
supercell_matrix=supercell_matrix,
|
supercell_matrix=supercell_matrix,
|
||||||
symmetrize_tensors=options.symmetrize_tensors,
|
symmetrize_tensors=options.symmetrize_tensors,
|
||||||
symprec=options.symprec)
|
symprec=options.symprec)
|
||||||
else:
|
else:
|
||||||
borns, epsilon, atom_indices = get_born_OUTCAR(
|
borns, epsilon, atom_indices = get_born_vasprunxml(
|
||||||
poscar_filename=poscar_filename,
|
filename=outcar_filename,
|
||||||
outcar_filename=outcar_filename,
|
|
||||||
primitive_matrix=primitive_axis,
|
primitive_matrix=primitive_axis,
|
||||||
supercell_matrix=supercell_matrix,
|
supercell_matrix=supercell_matrix,
|
||||||
symmetrize_tensors=options.symmetrize_tensors,
|
symmetrize_tensors=options.symmetrize_tensors,
|
||||||
|
|
Loading…
Reference in New Issue