def test_relocate_BZ_grid_address(self): for i, (cell, mesh, grid_address) in enumerate( zip(self.cells, self.meshes, self.grid_addresses)): reclat = np.linalg.inv(cell[0]) bz_grid_address, bz_map = relocate_BZ_grid_address(grid_address, mesh, reclat, is_dense=False) data_adrs = np.loadtxt(StringIO(result_bz_grid_address[i]), dtype='intc') np.testing.assert_equal(data_adrs, bz_grid_address) data_map = np.array([int(i) for i in result_bz_map[i].split()]) data_map[data_map == -1] = np.prod(mesh) * 8 np.testing.assert_equal(data_map, bz_map) # for i in range(len(bz_map) // 10): # print(("%3d " * 10) % tuple(bz_map[i * 10: (i + 1) * 10])) # n = len(bz_map) % 10 # print(("%3d " * n) % tuple(bz_map[-n:])) bz_grid_address, bz_map = relocate_BZ_grid_address(grid_address, mesh, reclat, is_dense=True) np.testing.assert_equal(data_adrs, bz_grid_address) np.testing.assert_equal(data_map, bz_map)
def test_relocate_BZ_grid_address(self): for i, (cell, mesh, grid_address) in enumerate( zip(self.cells, self.meshes, self.grid_addresses)): reclat = np.linalg.inv(cell[0]) bz_grid_address, bz_map = relocate_BZ_grid_address( grid_address, mesh, reclat, is_dense=False) data_adrs = np.loadtxt(StringIO(result_bz_grid_address[i]), dtype='intc') np.testing.assert_equal(data_adrs, bz_grid_address) data_map = np.array([int(i) for i in result_bz_map[i].split()]) data_map[data_map == -1] = np.prod(mesh) * 8 np.testing.assert_equal(data_map, bz_map) # for i in range(len(bz_map) // 10): # print(("%3d " * 10) % tuple(bz_map[i * 10: (i + 1) * 10])) # n = len(bz_map) % 10 # print(("%3d " * n) % tuple(bz_map[-n:])) bz_grid_address, bz_map = relocate_BZ_grid_address( grid_address, mesh, reclat, is_dense=True) np.testing.assert_equal(data_adrs, bz_grid_address) np.testing.assert_equal(data_map, bz_map)
def _set_ir_qpoints(self, rotations, is_time_reversal=True): grid_mapping_table, grid_address = get_stabilized_reciprocal_mesh( self._mesh, rotations, is_shift=self._is_shift, is_time_reversal=is_time_reversal, is_dense=True) shift = np.array(self._is_shift, dtype='intc') * 0.5 if self._fit_in_BZ: grid_address, _ = relocate_BZ_grid_address(grid_address, self._mesh, self._rec_lat, is_shift=self._is_shift, is_dense=True) self._grid_address = grid_address[:np.prod(self._mesh)] else: self._grid_address = grid_address (self._ir_grid_points, self._ir_weights) = extract_ir_grid_points(grid_mapping_table) self._ir_qpoints = np.array( (self._grid_address[self._ir_grid_points] + shift) / self._mesh, dtype='double', order='C') self._grid_mapping_table = grid_mapping_table
def test_get_grid_points_and_bz_grid_points_by_rotations(self): data = [[ 21, 31, 61, 55, 31, 61, 55, 21, 55, 21, 31, 61, 61, 55, 21, 31, 61, 55, 21, 31, 55, 21, 31, 61, 21, 31, 61, 55, 31, 61, 55, 21, 55, 21, 31, 61, 61, 55, 21, 31, 61, 55, 21, 31, 55, 21, 31, 61 ], [21, 30, 25, 31, 22, 27, 31, 22, 27, 21, 30, 25]] data_bz = [[ 21, 31, 61, 55, 31, 61, 55, 21, 55, 21, 31, 61, 61, 55, 21, 31, 61, 55, 21, 31, 55, 21, 31, 61, 21, 31, 61, 55, 31, 61, 55, 21, 55, 21, 31, 61, 61, 55, 21, 31, 61, 55, 21, 31, 55, 21, 31, 61 ], [21, 30, 25, 31, 22, 27, 56, 43, 52, 42, 55, 48]] for i, (cell, mesh, grid_address, rotations) in enumerate( zip(self.cells, self.meshes, self.grid_addresses, self.rotations)): rec_rots = [r.T for r in rotations] gps = get_grid_points_by_rotations([1, 1, 1], rec_rots, mesh) # print(", ".join(["%d" % g for g in gps])) np.testing.assert_equal(data[i], gps) bz_grid_address, bz_map = relocate_BZ_grid_address( grid_address, mesh, np.linalg.inv(cell[0])) bz_gps = get_BZ_grid_points_by_rotations([1, 1, 1], rec_rots, mesh, bz_map) # print(", ".join(["%d" % g for g in bz_gps])) np.testing.assert_equal(data_bz[i], bz_gps) diff_address = bz_grid_address[:len(grid_address)] - grid_address np.testing.assert_equal(diff_address % mesh, 0)
def _testBrillouinZone(self, direct_lat, mesh, is_shift): _, grid_address = get_stabilized_reciprocal_mesh(mesh, rotations=[ np.eye( 3, dtype='intc'), ], is_shift=is_shift) rec_lat = np.linalg.inv(direct_lat) bz_grid_address, bz_map = relocate_BZ_grid_address(grid_address, mesh, rec_lat, is_shift=is_shift) qpoints = (grid_address + np.array(is_shift) / 2.0) / mesh bz = BrillouinZone(rec_lat) bz.run(qpoints) sv_all = bz.shortest_qpoints # including BZ boundary duplicates sv = [v[0] for v in sv_all] bz_qpoints = (bz_grid_address + np.array(is_shift) / 2.0) / mesh d2_this = (np.dot(sv, rec_lat.T)**2).sum(axis=1) d2_spglib = (np.dot(bz_qpoints[:np.prod(mesh)], rec_lat.T)**2).sum(axis=1) diff = d2_this - d2_spglib diff -= np.rint(diff) # Following both of two tests are necessary. # Check equivalence of vectors by lattice translation np.testing.assert_allclose(diff, 0, atol=1e-8) # Check being in same (hopefull first) Brillouin zone by their lengths np.testing.assert_allclose(d2_this, d2_spglib, atol=1e-8)
def get_bz_grid_address(mesh, reciprocal_lattice, with_boundary=False): grid_address = get_grid_address(mesh) bz_grid_address, bz_map = spglib.relocate_BZ_grid_address( grid_address, mesh, reciprocal_lattice, is_dense=True) if with_boundary: return bz_grid_address, bz_map else: return bz_grid_address[:np.prod(mesh)]
def test_relocate_BZ_grid_address(self): for i, (cell, mesh, grid_address) in enumerate( zip(self.cells, self.meshes, self.grid_addresses)): reclat = np.linalg.inv(cell[0]) bz_grid_address, bz_map = relocate_BZ_grid_address( grid_address, mesh, reclat) data = np.loadtxt(StringIO(result_bz_grid_address[i]), dtype='intc') np.testing.assert_equal(data, bz_grid_address) data = [int(i) for i in result_bz_map[i].split()] np.testing.assert_equal(data, bz_map)
def test_get_grid_points_and_bz_grid_points_by_rotations(self): data = [[21, 31, 61, 55, 31, 61, 55, 21, 55, 21, 31, 61, 61, 55, 21, 31, 61, 55, 21, 31, 55, 21, 31, 61, 21, 31, 61, 55, 31, 61, 55, 21, 55, 21, 31, 61, 61, 55, 21, 31, 61, 55, 21, 31, 55, 21, 31, 61], [21, 30, 25, 31, 22, 27, 31, 22, 27, 21, 30, 25]] data_bz = [[21, 31, 61, 55, 31, 61, 55, 21, 55, 21, 31, 61, 61, 55, 21, 31, 61, 55, 21, 31, 55, 21, 31, 61, 21, 31, 61, 55, 31, 61, 55, 21, 55, 21, 31, 61, 61, 55, 21, 31, 61, 55, 21, 31, 55, 21, 31, 61], [21, 30, 25, 31, 22, 27, 56, 43, 52, 42, 55, 48]] for i, (cell, mesh, grid_address, rotations) in enumerate( zip(self.cells, self.meshes, self.grid_addresses, self.rotations)): rec_rots = [r.T for r in rotations] gps = get_grid_points_by_rotations([1, 1, 1], rec_rots, mesh, is_dense=False) # print(", ".join(["%d" % g for g in gps])) np.testing.assert_equal(data[i], gps) gps = get_grid_points_by_rotations([1, 1, 1], rec_rots, mesh, is_dense=True) np.testing.assert_equal(data[i], gps) bz_grid_address, bz_map = relocate_BZ_grid_address( grid_address, mesh, np.linalg.inv(cell[0])) bz_gps = get_BZ_grid_points_by_rotations([1, 1, 1], rec_rots, mesh, bz_map, is_dense=False) # print(", ".join(["%d" % g for g in bz_gps])) np.testing.assert_equal(data_bz[i], bz_gps) diff_address = bz_grid_address[:len(grid_address)] - grid_address np.testing.assert_equal(diff_address % mesh, 0) bz_gps = get_BZ_grid_points_by_rotations([1, 1, 1], rec_rots, mesh, bz_map, is_dense=True) np.testing.assert_equal(data_bz[i], bz_gps)
def get_nosym_triplets_at_q(grid_point, mesh, reciprocal_lattice, stores_triplets_map=False): grid_address = get_grid_address(mesh) bz_grid_address, bz_map = spglib.relocate_BZ_grid_address( grid_address, mesh, reciprocal_lattice, is_dense=True) map_triplets = np.arange(len(grid_address), dtype=bz_map.dtype) triplets_at_q, weights = _get_BZ_triplets_at_q(grid_point, bz_grid_address, bz_map, map_triplets, mesh) if not stores_triplets_map: map_triplets = None map_q = None else: map_q = map_triplets.copy() return triplets_at_q, weights, bz_grid_address, bz_map, map_triplets, map_q
def get_coarse_ir_grid_points(primitive, mesh, mesh_divisors, coarse_mesh_shifts, is_kappa_star=True, symprec=1e-5): mesh = np.array(mesh, dtype='intc') symmetry = Symmetry(primitive, symprec) point_group = symmetry.get_pointgroup_operations() if mesh_divisors is None: (ir_grid_points, ir_grid_weights, grid_address, grid_mapping_table) = get_ir_grid_points(mesh, point_group) else: mesh_divs = np.array(mesh_divisors, dtype='intc') coarse_mesh = mesh // mesh_divs if coarse_mesh_shifts is None: coarse_mesh_shifts = [False, False, False] if not is_kappa_star: coarse_grid_address = get_grid_address(coarse_mesh) coarse_grid_points = np.arange(np.prod(coarse_mesh), dtype='uintp') else: (coarse_ir_grid_points, coarse_ir_grid_weights, coarse_grid_address, coarse_grid_mapping_table) = get_ir_grid_points( coarse_mesh, point_group, mesh_shifts=coarse_mesh_shifts) ir_grid_points = from_coarse_to_dense_grid_points( mesh, mesh_divs, coarse_grid_points, coarse_grid_address, coarse_mesh_shifts=coarse_mesh_shifts) grid_address = get_grid_address(mesh) ir_grid_weights = ir_grid_weights reciprocal_lattice = np.linalg.inv(primitive.get_cell()) bz_grid_address, bz_map = spglib.relocate_BZ_grid_address( grid_address, mesh, reciprocal_lattice, is_dense=True) return (ir_grid_points, ir_grid_weights, bz_grid_address, grid_mapping_table)
def _set_ir_qpoints(self, rotations, is_time_reversal=True): grid_mapping_table, grid_address = get_stabilized_reciprocal_mesh( self._mesh, rotations, is_shift=self._is_shift, is_time_reversal=is_time_reversal, is_dense=True, ) # uintp to int_ grid_mapping_table = np.array(grid_mapping_table, dtype="int_") # Currently 'intc', but will be 'int_' in next major version. if int(__version__.split(".")[0]) < 3: dtype = "intc" else: dtype = "int_" if self._fit_in_BZ: grid_address, _ = relocate_BZ_grid_address( grid_address, self._mesh, self._rec_lat, is_shift=self._is_shift, is_dense=True, ) self._grid_address = np.array(grid_address[:np.prod(self._mesh)], dtype=dtype, order="C") else: self._grid_address = np.array(grid_address, dtype=dtype, order="C") (self._ir_grid_points, self._ir_weights) = extract_ir_grid_points(grid_mapping_table) shift = np.array(self._is_shift) * 0.5 self._ir_qpoints = np.array( (self._grid_address[self._ir_grid_points] + shift) / self._mesh, dtype="double", order="C", ) self._grid_mapping_table = grid_mapping_table
def get_triplets_at_q( grid_point, mesh, point_group, # real space point group of space group reciprocal_lattice, # column vectors is_time_reversal=True, swappable=True, stores_triplets_map=False): """Parameters ---------- grid_point : int A grid point mesh : array_like Mesh numbers shape=(3,), dtype='intc' point_group : array_like Rotation matrices in real space. Note that those in reciprocal space mean these matrices transposed (local terminology). shape=(n_rot, 3, 3), dtype='intc', order='C' reciprocal_lattice : array_like Reciprocal primitive basis vectors given as column vectors shape=(3, 3), dtype='double', order='C' is_time_reversal : bool, optional Inversion symemtry is added if it doesn't exist. Default is True. swappable : bool, optional q1 and q2 among (q0, q1, q2) can be swapped. Deafult is True. Returns ------- triplets_at_q : ndarray Symmetry reduced number of triplets are stored as grid point integer numbers. shape=(n_triplets, 3), dtype='uintp' weights : ndarray Weights of triplets in Brillouin zone shape=(n_triplets,), dtype='intc' bz_grid_address : ndarray Integer grid address of the points in Brillouin zone including surface. The first prod(mesh) numbers of points are independent. But the rest of points are translational-symmetrically equivalent to some other points. shape=(n_grid_points, 3), dtype='intc', order='C' bz_map : ndarray Grid point mapping table containing BZ surface. See more detail in spglib docstring. shape=(prod(mesh*2),), dtype='uintp' map_tripelts : ndarray or None Returns when stores_triplets_map=True, otherwise None is returned. Mapping table of all triplets to symmetrically independent tripelts. More precisely, this gives a list of index mapping from all q-points to independent q' of q+q'+q''=G. Considering q' is enough because q is fixed and q''=G-q-q' where G is automatically determined to choose smallest |G|. shape=(prod(mesh),), dtype='uintp' map_q : ndarray or None Returns when stores_triplets_map=True, otherwise None is returned. Irreducible q-points stabilized by q-point of specified grid_point. shape=(prod(mesh),), dtype='uintp' """ map_triplets, map_q, grid_address = _get_triplets_reciprocal_mesh_at_q( grid_point, mesh, point_group, is_time_reversal=is_time_reversal, swappable=swappable) bz_grid_address, bz_map = spglib.relocate_BZ_grid_address( grid_address, mesh, reciprocal_lattice, is_dense=True) triplets_at_q, weights = _get_BZ_triplets_at_q(grid_point, bz_grid_address, bz_map, map_triplets, mesh) assert np.prod(mesh) == weights.sum(), \ "Num grid points %d, sum of weight %d" % ( np.prod(mesh), weights.sum()) # These maps are required for collision matrix calculation. if not stores_triplets_map: map_triplets = None map_q = None return triplets_at_q, weights, bz_grid_address, bz_map, map_triplets, map_q