"""
.. module:: utility
:synopsis: Contains several functions to calculate the interaction energies.
.. moduleauthor:: D. Wang <dwang5@zoho.com>
"""
import os.path
from netCDF4 import Dataset
import numpy as np
[docs]def calc_madelung_cc(mat, alloy_fn):
"""
Args:
* 'mat' is the charge-charge interaction matrix.
* 'alloy_fn' specifies the distribution of charges.
Calculate the Madelung constant due to the charge-charge interaction.
"""
dum_1 = Dataset(alloy_fn, 'r')
config = dum_1['matrix']
delung = 0.0
c1 = config[0]
# print(config.shape[:])
for i in range(config.shape[0]):
delung += c1 * mat[i] * config[i]
return delung
[docs]def calc_madelung_dd(mat, alloy_fn):
"""
Args:
* 'mat' is the dipole-dipole interaction matrix.
* 'alloy_fn' specifies the dipole configuration.
Calculate the "Madelung constant" due to the dipole-dipole interaction.
"""
dum_1 = Dataset(alloy_fn, 'r')
config = dum_1['matrix']
delung = 0.0
v1 = np.array([config[0, 0], config[0, 1], config[0, 2]])
for i in range(config.shape[0]):
dum = np.array([
[mat[i, 0], mat[i, 5], mat[i, 4]],
[mat[i, 5], mat[i, 1], mat[i, 3]],
[mat[i, 4], mat[i, 3], mat[i, 2]]
])
v2 = np.array([config[i, 0], config[i, 1], config[i, 2]])
delung += np.dot(v1, np.dot(dum, v2))
return delung
[docs]def calc_madelung_cd(mat, alloy_fn, alloy_hn, alloy):
"""
Args:
* 'mat' is the charge-dipole interaction matrix.
* 'alloy_fn' is the charge configuration.
* 'alloy_hn' is the dipole configuration.
* 'alloy' file contains the information to map index between 3D and 1D for easy use in this funciton.
"""
dum_1 = Dataset(alloy_fn, 'r')
config_c = dum_1['matrix']
dum_2 = Dataset(alloy_hn, 'r')
config_d = dum_2['matrix']
delung = 0.0
assert (config_d.shape[0] == alloy.nsites)
assert (config_c.shape[0] == alloy.nsites)
for i in range(config_c.shape[0]):
c2 = config_c[i]
for j in range(config_d.shape[0]):
v1 = np.array([config_d[j, 0], config_d[j, 1], config_d[j, 2]])
ix = alloy.ixa[j] - alloy.ixa[i]
iy = alloy.iya[j] - alloy.iya[i]
iz = alloy.iza[j] - alloy.iza[i]
ixi = ix + alloy.n1
iyi = iy + alloy.n2
izi = iz + alloy.n3
dist = alloy.iaa[abs(ix), abs(iy), abs(iz)]
dum = np.array([
mat[ixi, iyi, izi, 0],
mat[ixi, iyi, izi, 1],
mat[ixi, iyi, izi, 2]])
delung += c2 * np.dot(dum, v1)
return delung / alloy.nsites