Source code for ase2sprkkr.asr.utils.calculator_utils

"""Module contaning calculator utility functions.

The functions in this module basically only take a calculator as
essential arguments. Additional, non-essential arguments are allowed.

"""


[docs] def get_eigenvalues(calc): """Get eigenvalues from calculator. Parameters ---------- calc : Calculator Returns ------- e_skn: (ns, nk, nb)-shape array """ import numpy as np rs = range(calc.get_number_of_spins()) rk = range(len(calc.get_ibz_k_points())) e = calc.get_eigenvalues return np.asarray([[e(spin=s, kpt=k) for k in rk] for s in rs])
[docs] def fermi_level(calc, eigenvalues=None, nelectrons=None, nspins=None): """Get Fermi level at T=0 from calculation. This works by filling in the appropriate number of electrons. Parameters ---------- calc : ASE Calculator ASE calculator eigenvalues : ndarray, shape=(nspins, nkpoints, nbands) eigenvalues (taken from calc if None) nelectrons : float, optional number of electrons (taken from calc if None) nspins : int Number of spins that eigenvalues are provided for (default=2). Ie. 2 when both spin-channels are represented in eps_skn or 1 if only 1 spin-channel is represented in eps_skn. Returns ------- fermi_level : float fermi level in eV """ import numpy as np if nelectrons is None: nelectrons = calc.get_number_of_electrons() if eigenvalues is None: eigenvalues = get_eigenvalues(calc) nspins = calc.get_number_of_spins() else: assert nspins is not None, 'You have to provide a number of spins!' eigenvalues_skn = eigenvalues # More intuitive variable name eig_shape = eigenvalues_skn.shape assert len(eig_shape) == 3, f'Bad shape of eigenvalues: {eig_shape}.' nkpts = len(calc.get_bz_k_points()) # The number of occupied states is the number of electrons # multiplied by the number of k-points nocc = int(nelectrons * nkpts) if eig_shape[1] == nkpts: count_k = np.ones(nkpts, int) else: weight_k = np.array(calc.get_k_point_weights()) count_k = np.round(weight_k * nkpts).astype(int) if nspins == 1: count_k *= 2 eps_N = np.repeat(eigenvalues_skn, count_k, axis=1).ravel() eps_N.sort() homo = eps_N[nocc - 1] lumo = eps_N[nocc] fermi_level = (homo + lumo) / 2 return fermi_level