Source code for supercell

"""
.. module:: Supercell
    :synopsis: Framework for constructing supercells.

.. moduleauthor:: D. Wang <dwang5@zoho.com>
"""

from math import atan
import numpy as np

[docs]class Supercell(object): """ Args: n1,n2,n3 are the number of repeated unitcells along the three directions of the 'lattice'. lattice specifies the Bravais lattice of a **unit cell**. .. note:: This version is not compitable with previous ones as * All the index starts from 0. * Arrays (e.g. lattice and reci lattice) are row majored. The reason is to use Pybind11 that binds to C++ instead of Fortran. """ def __init__(self,n1,n2,n3,lattice): """ Define most essential components of a supercell. """ self.n1 = n1 self.n2 = n2 self.n3 = n3 self.nsites = n1*n2*n3 self.nxy = n1*n2 #Lattice vector (Bravais vector) self.a = np.zeros((3,3)) self.b = np.zeros((3,3)) self.lattice = np.zeros((3,3)) self.lattice = lattice self.set_supercell() self.celvol = self.volcell() #Calculate reciprocal lattice. self.rec_lat()
[docs] def set_supercell(self): """ Multiply the n1,n2,n3 to the unitcell vectors to form the superlattice. """ self.a[0, :] = self.n1 * self.lattice[0, :] self.a[1, :] = self.n2 * self.lattice[1, :] self.a[2, :] = self.n3 * self.lattice[2, :] #'XYPOINTS' self.ix = np.zeros(self.nxy,dtype=np.int) self.iy = np.zeros(self.nxy,dtype=np.int) self.site = np.zeros((self.n1,self.n2),dtype=np.int) nxy = 0 for i in range(self.n1): for j in range(self.n2): self.ix[nxy] = i self.iy[nxy] = j nxy += 1 self.site[i,j] = nxy # Match ia with ix, iy, and iz. # This is the convention in all the following. self.iaa = np.zeros((self.n1,self.n2,self.n3),dtype=np.int) self.ixa = np.zeros(self.nsites,dtype=np.int) self.iya = np.zeros(self.nsites,dtype=np.int) self.iza = np.zeros(self.nsites,dtype=np.int) l = 0 for k in range(self.n3): for j in range(self.n2): for i in range(self.n1): self.iaa[i,j,k] = l self.ixa[l] = i self.iya[l] = j self.iza[l] = k l +=1
#for i in range(self.nsites): # print(i,self.ixa[i],self.iya[i],self.iza[i])
[docs] def volcell(self): """ Volume of the supercell. """ return np.inner(self.a[0,:], np.cross(self.a[1,:], self.a[2,:]))
[docs] def rec_lat(self): """ Calculates reciprocal lattice vectors. The convention follows "Solid state physics" by Lu Dong, Jiang Ping ... Eq. (2.2.2) """ pi = 4.0 * atan(1.0) self.b[0,:] = np.cross(self.a[1,:],self.a[2,:])*2*pi/self.celvol self.b[1,:] = np.cross(self.a[2,:],self.a[0,:])*2*pi/self.celvol self.b[2,:] = np.cross(self.a[0,:],self.a[1,:])*2*pi/self.celvol