pyextal.jaxMultipole.model

Hansen-Coppens multipole model of X-ray and electron structure factors.

Atomic density, in the atom’s local frame (Hansen & Coppens 1978):

\[\rho(\mathbf r) = P_c \rho_c(r) + \sum_{\rm shells} P_v \kappa^3 \rho_v(\kappa r) + \sum_{l=0}^{l_{max}} \kappa'^3 R_l(\kappa' r) \sum_m P_{lm} d_{lm}(\hat r),\]

with R_l = zeta^(n_l+3)/(n_l+2)! r^n_l exp(-zeta r). Its form factor, with k = 4 pi s and the engine’s exp(+2 pi i h.r) phase convention,

\[f(\mathbf h) = P_c f_c(k) + \sum P_v f_v(k/\kappa) + \sum_l 4\pi i^l \langle j_l \rangle(k; \kappa'\zeta_l, n_l) \sum_m P_{lm} d_{lm}(\hat{\mathbf k}_{\rm loc}).\]

The 4 pi i^l comes from the plane-wave expansion; it multiplies the same density-normalised d_lm because d_lm is a constant multiple of the wavefunction-normalised harmonic.

Crystal sums, over the whole group modulo lattice translations (inversion and centring included) divided by the order of each site’s stabiliser:

\[\begin{split}F_x(\mathbf h) &= \sum_j \frac{o_j}{|S_j|} \sum_{(W,w)} f_j(W^T\mathbf h)\, T_j(W^T\mathbf h)\, e^{2\pi i \mathbf h\cdot(W\mathbf x_j + \mathbf w)} \\ U_{\mathbf h} &= \frac{\gamma}{\pi\Omega} \sum_j \frac{o_j}{|S_j|} \sum_{(W,w)} \frac{M}{s^2}\,[Z_j - f_j(W^T\mathbf h)]\, T_j\, e^{\ldots}\end{split}\]

with T_j(h) = exp(-h^T beta_j h), M = 0.023933754 (Mott-Bethe), gamma = 1 + 1.9569341e-3 kV, Omega the cell volume. This is exactly the engine’s sfsub.f90 (which transforms the reflection, not the atom, so the asymmetric atom’s own frame serves for all its images). The sum over the full group also projects any populations onto the site-allowed ones, so a model can never smuggle in a forbidden multipole – which is also how it is tested.

Modes

'hc'

The multipole model above, radial functions from an XD bank.

'cm'

The engine’s independent-atom model: Cromer-Mann f_x from sftabl.sct with the engine’s Z_eff (sum a + c for two-letter labels, the true Z for ion labels; xtal0.f90:405-416). Only ADPs are meaningful. Reproducing defaultsf(3, g) in this mode validates every piece of bookkeeping – orbits, phases, ADPs, gamma, Omega – independently of the radial functions.

param The model takes one flat physical vector p laid out by Layout:

type The model takes one flat physical vector p laid out by Layout:

per

param site Pv (per valence shell):

param kappa (per shell:

param or one shared):

:param : :param kappa_p: :param the P_lm up to the site’s lmax and the six U_ij: :param (crystallographic: :param Angstrom^2). Which of them are refined: :param tied or restrained: :param is jaxMultipole.params’s business; the model just evaluates.:

Classes

AtomSpec

How one site is modelled.

Layout

Names and positions of the physical parameters.

MultipoleModel

Structure factors of a crystal under a multipole model.

Functions

deformation_orbital(config)

The valence orbital whose single-zeta exponent sets the deformation functions.

default_n_l(orbital_name, lmax)

Hansen-Coppens default powers: n_l = max(2(n-1), l) of the orbital n.

Module Contents

pyextal.jaxMultipole.model.deformation_orbital(config)

The valence orbital whose single-zeta exponent sets the deformation functions.

The one with the highest l, so 3d over 4s for Ti and 2p over 2s for O; None for an atom without valence orbitals.

pyextal.jaxMultipole.model.default_n_l(orbital_name, lmax)

Hansen-Coppens default powers: n_l = max(2(n-1), l) of the orbital n.

Gives (2, 2, 2, 3, 4) for a 2p atom (O), 4 throughout for 3d (Ti, Ni), 6 for 4d, 8 for 5d and for 5s (Sr). Pass explicit n_l to follow another convention (XD uses 4, 4, 6, 8 for second-row p atoms, for instance).

class pyextal.jaxMultipole.model.AtomSpec

How one site is modelled.

Variables:
  • site (str) – Site label in the Crystal.

  • mode (str) – 'hc' or 'cm'.

  • bank (str) – XD bank ('RDF_SCM', 'PBE-QZ4P-ZORA' or a path).

  • key (str, optional) – Bank entry; the element by default.

  • valence (list[str], optional) – Valence orbitals (bank default if None).

  • occupations (dict, optional) – Orbital occupation overrides.

  • core_from (str, optional) – Bank entry supplying the core.

  • shells (str) – 'joined' (one Pv for all valence orbitals) or 'separate'.

  • kappa_shared (bool) – One kappa for all valence shells.

  • lmax (int) – Highest deformation order, -1 for none.

  • n_l (tuple, optional) – Radial powers per l; default_n_l if None.

  • zeta (float | sequence, optional) – Deformation exponent (bohr^-1) before kappa’ – one value for every l, or one per l (lmax + 1 values; e.g. VALRAY’s separate alpha_l). Twice the single-zeta exponent of deformation_orbital if None.

  • frame (tuple, optional) – (z, x) direct-lattice directions of the local axes; automatic if None (jaxMultipole.symmetry.local_frame).

site: str
mode: str = 'hc'
bank: str = 'RDF_SCM'
key: str = None
valence: list = None
occupations: dict = None
core_from: str = None
shells: str = 'joined'
kappa_shared: bool = True
lmax: int = 4
n_l: tuple = None
zeta: object = None
frame: tuple = None
class pyextal.jaxMultipole.model.Layout

Names and positions of the physical parameters.

Variables:
  • names (list[str]) – 'Ti1.Pv', 'Ti1.kappa', 'O1.P20', 'O1.U11', …

  • p0 (np.ndarray) – Default values (neutral valence populations, kappa = 1, P_lm = 0, U from the crystal).

names: list
p0: numpy.ndarray
__post_init__()
__len__()
__getitem__(name)
__contains__(name)
site_names(site)
class pyextal.jaxMultipole.model.MultipoleModel(crystal, specs=())

Structure factors of a crystal under a multipole model.

Parameters:
  • crystal (Crystal) – The crystal.

  • specs (list[AtomSpec] | dict) – One spec per site, or label -> spec keyword dict; sites without a spec get AtomSpec(site).

crystal
sites = []
layout
_resolve(i, site, spec)
_build_layout()
geometry(hkl)

Everything about a set of reflections that does not depend on p.

Parameters:

hkl (array-like) – (nh, 3) reflections; 000 is not allowed.

Returns:

NumPy arrays: hkl, s, k (bohr^-1), Q (the six ADP quadratic forms per operation), and per site phase (complex, (nh, nops)) and Y (harmonics of the local directions, (nh, nops, (lmax+1)^2)).

Return type:

dict

_beta_matrix()
_site_terms(p, geo, j, dtype)

(f_sph (nh,), f_aniso (nh, nops) | None, T (nh, nops)) of site j.

_crystal_sum(p, geo, electron, static)
ug(p, geo)

Electron structure factors, Angstrom^-2 (complex).

fx(p, geo, static=False)

X-ray structure factors, electrons (complex); static drops the ADPs.

electrons(p)

Electrons in the cell: sum occ * mult * (Pc + sum Pv + P00).

nuclear_charge()
describe()

One line per site: mode, partition, frame, allowed functions.