refnx.reflect

class refnx.reflect.Component(name='')[source]

Bases: object

A base class for describing the structure of a subset of an interface.

Parameters

name (str, optional) – The name associated with the Component

Notes

By setting the Component.interfaces property one can control the type of interfacial roughness between all the layers of an interfacial profile.

__mul__(n)[source]

MUL’ing components makes them repeat.

Parameters

n (int) – How many times you want to repeat the Component

Returns

s – The created Structure

Return type

refnx.reflect.Structure

__or__(other)[source]

OR’ing components can create a Structure.

Parameters

other (refnx.reflect.Structure, refnx.reflect.Component) – Combines with this component to make a Structure

Returns

s – The created Structure

Return type

refnx.reflect.Structure

Examples

>>> air = SLD(0, name='air')
>>> sio2 = SLD(3.47, name='SiO2')
>>> si = SLD(2.07, name='Si')
>>> structure = air | sio2(20, 3) | si(0, 3)
__str__()[source]

Return str(self).

property interfaces

The interfacial roughness type between each layer in Component.slabs. Should be one of {None, Interface, or sequence of Interface}.

logp()[source]

The log-probability that this Component adds to the total log-prior term. Do not include log-probability terms for the actual parameters, these are automatically included elsewhere.

Returns

logp – Log-probability

Return type

float

property parameters

refnx.analysis.Parameters associated with this component

slabs(structure=None)[source]

The slab representation of this component

Parameters

structure (refnx.reflect.Structure) – The Structure hosting the Component.

Returns

  • slabs (np.ndarray) – Slab representation of this Component. Has shape (N, 5).

    • slab[N, 0]

      thickness of layer N

    • slab[N, 1]

      SLD.real of layer N (not including solvent)

    • slab[N, 2]

      SLD.imag of layer N (not including solvent)

    • slab[N, 3]

      roughness between layer N and N-1

    • slab[N, 4]

      volume fraction of solvent in layer N.

  • If a Component returns None, then it doesn’t have any slabs.

class refnx.reflect.Erf[source]

Bases: Interface

An Error function interfacial profile

Notes

Svechnikov, M.; Pariev, D.; Nechay, A.; Salashchenko, N.; Chkhalo, N.; Vainer, Y. & Gaman, D., “Extended model for the reconstruction of periodic multilayers from extreme ultraviolet and X-ray reflectivity data”, Journal of Applied Crystallography, 2017, 50, 1428-1440

__call__(z, scale=1, loc=0)[source]

Call self as a function.

class refnx.reflect.Exponential[source]

Bases: Interface

An Exponential interfacial profile

Notes

Stearns, D. G. J. Appl. Phys., 1989, 65, 491–506.

__annotations__ = {}
__call__(z, scale=1, loc=0)[source]

Call self as a function.

class refnx.reflect.FresnelTransform(sld_fronting, sld_backing, dq=0)[source]

Bases: Transform

Fresnel transform for data.

Divides experimental signal by reflectivity from an infinitely sharp interface.

Parameters
  • sld_fronting (float) – SLD of fronting medium

  • sld_backing (float) – SLD of backing medium

  • dq (float, array-like optional) –

    • dq == 0

      no resolution smearing is employed.

    • dq is a float

      a constant dQ/Q resolution smearing is employed. For 5% resolution smearing supply 5.

    • dq is array-like

      the array contains the FWHM of a Gaussian approximated resolution kernel. Point by point resolution smearing is employed. Use this option if dQ/Q varies across your dataset.

Notes

Using a null reflectivity system (sld_fronting == sld_backing) will lead to ZeroDivisionError. If point-by-point resolution smearing is employed then a unique transform must be created for each Objective. This is because the number of points in dq must be the same as x.size when FresnelTransform.transform is called.

__annotations__ = {}
__call__(x, y, y_err=None, x_err=0)[source]

Calculate the transformed data

Parameters
  • x (array-like) – x-values

  • y (array-like) – y-values

  • y_err (array-like) – Uncertainties in y (standard deviation)

  • x_err (array-like) – Uncertainties in x (FWHM)

Returns

yt, et – The transformed data

Return type

tuple

class refnx.reflect.Interface[source]

Bases: object

Defines an Interfacial profile

__annotations__ = {}
__call__(z, scale=1, loc=0)[source]

Call self as a function.

class refnx.reflect.Linear[source]

Bases: Interface

A Linear function interfacial profile

Notes

Stearns, D. G. J. Appl. Phys., 1989, 65, 491–506.

__annotations__ = {}
__call__(z, scale=1, loc=0)[source]

Call self as a function.

class refnx.reflect.LipidLeaflet(apm, b_heads, vm_heads, thickness_heads, b_tails, vm_tails, thickness_tails, rough_head_tail, rough_preceding_mono, head_solvent=None, tail_solvent=None, reverse_monolayer=False, name='')[source]

Bases: Component

Describes a lipid leaflet Component at an interface

Parameters
  • APM (float or refnx.analysis.Parameter) –

  • b_heads (float, refnx.analysis.Parameter, complex or SLD) – Sum of coherent scattering lengths of head group (Angstrom). When an SLD is provided it is simply an easy way to provide a complex value. LipidLeaflet.b_heads_real is set to SLD.real, etc.

  • vm_heads (float or refnx.analysis.Parameter) – Molecular volume of head group (Angstrom**2)

  • thickness_heads (float or refnx.analysis.Parameter) – Thickness of head group region (Angstrom)

  • b_tails (float, refnx.analysis.Parameter, complex or SLD) – Sum of coherent scattering lengths of tail group (Angstrom). When an SLD is provided it is simply an easy way to provide a complex value. LipidLeaflet.b_tails_real is set to SLD.real, etc.

  • vm_tails (float or refnx.analysis.Parameter) – Molecular volume of tail group (Angstrom**2)

  • thickness_tails (float or refnx.analysis.Parameter) – Thickness of head group region (Angstrom)

  • rough_head_tail (float or refnx.analysis.Parameter) – Roughness of head-tail group (Angstrom)

  • rough_preceding_mono (float or refnx.analysis.Parameter) – Roughness between preceding component (in the fronting direction) and the monolayer (Angstrom). If reverse_monolayer is False then this is the roughness between the preceding component and the heads, if reverse_monolayer is True then this is the roughness between the preceding component and the tails.

  • head_solvent (None, float, complex, refnx.reflect.SLD) – Solvent for the head region. If None, then solvation will be performed by the parent Structure, using the Structure.solvent attribute. Other options are coerced to an SLD object using SLD(float | complex). A float/complex argument is the SLD of the solvent (10**-6 Angstrom**-2).

  • tail_solvent (None, float, complex, refnx.reflect.SLD) – Solvent for the tail region. If None, then solvation will be performed by the parent Structure, using the Structure.solvent attribute. Other options are coerced to an SLD object using SLD(float | complex). A float/complex argument is the SLD of the solvent (10**-6 Angstrom**-2).

  • reverse_monolayer (bool, optional) – The default is to have heads closer to the fronting medium and tails closer to the backing medium. If reverse_monolayer is True then the tails will be closer to the fronting medium and heads closer to the backing medium.

  • name (str, optional) – The name for the component

Notes

The sum of coherent scattering lengths must be in Angstroms, the volume must be in cubic Angstroms. This is because the SLD of a tail group is calculated as b_tails / vm_tails * 1e6 to achieve the units 10**6 Angstrom**-2.

__annotations__ = {}
logp()[source]

The log-probability that this Component adds to the total log-prior term. Do not include log-probability terms for the actual parameters, these are automatically included elsewhere.

Returns

logp – Log-probability

Return type

float

make_constraint(objective)[source]

Creates a NonlinearConstraint for a LipidLeaflet, ensuring that volume fraction of lipid in the head+tail regions lies in [0, 1]. Suitable for use by differential_evolution.

Parameters

objective (refnx.analysis.Objective) – Objective containing the LipidLeaflet. Must be the Objective that is being minimised by differential_evolution.

Returns

nlc

Return type

NonlinearConstraint

Notes

You must create separate constraints for each LipidLeaflet object in your system. The Objective you supply must be for the overall curve fitting system. i.e. possibly a GlobalObjective.

Examples

>>> # leaflet is a LipidLeaflet, used in an Objective, obj
>>> con = leaflet.make_constraint(obj)
>>> fitter = CurveFitter(obj)
>>> fitter.fit("differential_evolution", constraints=(con,))
property parameters

refnx.analysis.Parameters associated with this component

slabs(structure=None)[source]

Slab representation of monolayer, as an array

Parameters

structure (refnx.reflect.Structure) – The Structure hosting this Component

property volfrac_h
property volfrac_t
class refnx.reflect.MaterialSLD(formula, density, probe='neutron', wavelength=1.8, name='')[source]

Bases: Scatterer

Object representing SLD of a chemical formula. You can fit the mass density of the material.

Parameters
  • formula (str) – Chemical formula

  • density (float or Parameter) – mass density of compound in g / cm**3

  • probe ({'x-ray', 'neutron'}, optional) – Are you using neutrons or X-rays?

  • wavelength (float, optional) – wavelength of radiation (Angstrom)

  • name (str, optional) – Name of material

Notes

You need to have the periodictable package installed to use this object. An SLD object can be used to create a Slab:

>>> # a MaterialSLD object representing Silicon Dioxide
>>> sio2 = MaterialSLD('SiO2', 2.2, name='SiO2')
>>> # create a silica slab of SiO2 20 A in thickness, with a 3 A roughness
>>> sio2_layer = sio2(20, 3)
>>> # allow the mass density of the silica to vary between 2.1 and 2.3
>>> # g/cm**3
>>> sio2.density.setp(vary=True, bounds=(2.1, 2.3))
__complex__()[source]
complex(wavelength)[source]

Wavelength dispersive evaluation of a Scatterer SLD/RI

Parameters

wavelength (float) –

Returns

sldc

Return type

complex

property formula
property parameters
class refnx.reflect.MixedReflectModel(structures, scales=None, bkg=1e-07, name='', dq=5.0, threads=-1, quad_order=17, dq_type='pointwise', q_offset=0.0)[source]

Bases: object

Calculates an incoherent average of reflectivities from a sequence of structures. Such a situation may occur if a sample is not uniform over its illuminated area.

Parameters
  • structures (sequence of refnx.reflect.Structure) – The interfacial structures to incoherently average

  • scales (None, sequence of float or refnx.analysis.Parameter, optional) – scale factors. The reflectivities calculated from each of the structures are multiplied by their respective scale factor during overall summation. These values are turned into Parameters during the construction of this object. You must supply a scale factor for each of the structures. If scales is None, then default scale factors are used: [1 / len(structures)] * len(structures). It is a good idea to set the lower bound of each scale factor to zero (not done by default).

  • bkg (float or refnx.analysis.Parameter, optional) – linear background added to the overall reflectivity. This is turned into a Parameter during the construction of this object.

  • name (str, optional) – Name of the mixed Model

  • dq (float or refnx.analysis.Parameter, optional) –

    • dq == 0 then no resolution smearing is employed.

    • dq is a float or refnx.analysis.Parameter

      a constant dQ/Q resolution smearing is employed. For 5% resolution smearing supply 5.

    However, if x_err is supplied to the model method, then that overrides any setting given here. This value is turned into a Parameter during the construction of this object.

  • threads (int, optional) – Specifies the number of threads for parallel calculation. This option is only applicable if you are using the _creflect module. The option is ignored if using the pure python calculator, _reflect. If threads == -1 then all available processors are used.

  • quad_order (int, optional) – the order of the Gaussian quadrature polynomial for doing the resolution smearing. default = 17. Don’t choose less than 13. If quad_order == ‘ultimate’ then adaptive quadrature is used. Adaptive quadrature will always work, but takes a _long_ time (2 or 3 orders of magnitude longer). Fixed quadrature will always take a lot less time. BUT it won’t necessarily work across all samples. For example, 13 points may be fine for a thin layer, but will be atrocious at describing a multilayer with bragg peaks.

  • dq_type ({'pointwise', 'constant'}, optional) – Chooses whether pointwise or constant dQ/Q resolution smearing (see dq keyword) is used. To use pointwise smearing the x_err keyword provided to Objective.model method must be an array, otherwise the smearing falls back to ‘constant’.

  • q_offset (float or refnx.analysis.Parameter, optional) – Compensates for uncertainties in the angle at which the measurement is performed. A positive/negative q_offset corresponds to a situation where the measured q values (incident angle) may have been under/over estimated, and has the effect of shifting the calculated model to lower/higher effective q values.

__call__(x, p=None, x_err=None)[source]

Calculate the generative model

Parameters
  • x (float or np.ndarray) – q values for the calculation.

  • p (refnx.analysis.Parameters, optional) – parameters required to calculate the model

  • x_err (np.ndarray) – dq resolution smearing values for the dataset being considered.

Returns

reflectivity – Calculated reflectivity

Return type

np.ndarray

property bkg

refnx.analysis.Parameter - linear background added to all model values.

property dq

refnx.analysis.Parameter

  • dq.value == 0

    no resolution smearing is employed.

  • dq.value > 0

    a constant dQ/Q resolution smearing is employed. For 5% resolution smearing supply 5. However, if x_err is supplied to the model method, then that overrides any setting reported here.

logp()[source]

Additional log-probability terms for the reflectivity model. Do not include log-probability terms for model parameters, these are automatically calculated elsewhere.

Returns

logp – log-probability of structure.

Return type

float

model(x, p=None, x_err=None)[source]

Calculate the reflectivity of this model

Parameters
  • x (float or np.ndarray) – q values for the calculation.

  • p (refnx.analysis.Parameter, optional) – parameters required to calculate the model

  • x_err (np.ndarray) – dq resolution smearing values for the dataset being considered.

Returns

reflectivity

Return type

np.ndarray

property parameters

refnx.analysis.Parameters - parameters associated with this model.

property q_offset

refnx.analysis.Parameter - compensates for any angular misalignment during an experiment.

property scales

refnx.analysis.Parameter - the reflectivity from each of the structures are multiplied by these values to account for patchiness.

property structures

list of refnx.reflect.Structure that describe the patchiness of the surface.

class refnx.reflect.MixedSlab(thick, sld_list, vf_list, rough, name='', vfsolv=0, interface=None)[source]

Bases: Component

A slab component made of several components

Parameters
  • thick (refnx.analysis.Parameter or float) – thickness of slab (Angstrom)

  • sld_list (sequence of {refnx.reflect.Scatterer, complex, float}) – Sequence of (complex) SLDs that are contained in film (/1e-6 Angstrom**-2)

  • vf_list (sequence of refnx.analysis.Parameter or float) – relative volume fractions of each of the materials contained in the film.

  • rough (refnx.analysis.Parameter or float) – roughness on top of this slab (Angstrom)

  • name (str) – Name of this slab

  • vfsolv (refnx.analysis.Parameter or float) – Volume fraction of solvent [0, 1]

  • interface ({Interface, None}, optional) – The type of interfacial roughness associated with the Slab. If None, then the default interfacial roughness is an Error function (also known as Gaussian roughness).

Notes

The SLD of this Slab is calculated using the normalised volume fractions of each of the constituent Scatterers:

>>> np.sum([complex(sld) * vf / np.sum(vf_list) for sld, vf in
...         zip(sld_list, vf_list)]).

The overall SLD then takes into account the volume fraction of solvent, vfsolv.

__annotations__ = {}
__str__()[source]

Return str(self).

property parameters

refnx.analysis.Parameters associated with this component

slabs(structure=None)[source]

Slab representation of this component. See Component.slabs

class refnx.reflect.Motofit[source]

Bases: object

An interactive slab modeller (Jupyter/ipywidgets based) for Neutron and X-ray reflectometry data.

The interactive modeller is designed to be used in a Jupyter notebook.

>>> # specify that plots are in a separate graph window
>>> %matplotlib qt
>>> # alternately if you want the graph to be embedded in the notebook use
>>> # %matplotlib notebook
>>> from refnx.reflect import Motofit
>>> # create an instance of the modeller
>>> app = Motofit()
>>> # display it in the notebook by calling the object with a datafile.
>>> app('dataset1.txt')
>>> # lets fit a different dataset
>>> app2 = Motofit()
>>> app2('dataset2.txt')

The Motofit instance has several useful attributes that can be used in other cells. For example, one can access the objective and curvefitter attributes for more advanced fitting functionality than is available in the GUI. A code attribute can be used to retrieve a Python code fragment that can be used as a basis for developing more complicated models, such as interparameter constraints, global fitting, etc.

dataset

The dataset associated with the modeller

Type

refnx.dataset.Data1D

model

Calculates a theoretical model, from an interfacial structure (model.Structure).

Type

refnx.reflect.ReflectModel

objective

The Objective that allows one to compare the model against the data.

Type

refnx.analysis.Objective

fig

Graph displaying the data.

Type

matplotlib.figure.Figure

__call__(data=None, model=None)[source]

Display the Motofit GUI in a Jupyter notebook cell.

Parameters
  • data (refnx.dataset.Data1D) – The dataset to associate with the Motofit instance.

  • model (refnx.reflect.ReflectModel or str or file-like) – A model to associate with the data. If model is a str or file-like then the load_model method will be used to try and load the model from file. This assumes that the file is a pickle of a ReflectModel

property code

A Python code fragment capable of fitting the data. Executable Python code fragment for the GUI model.

Type

str

property curvefitter

Object for fitting the data based on the objective.

Type

class

Type

CurveFitter

do_fit(*args)[source]

Ask the Motofit object to perform a fit (differential evolution).

Parameters

change

Notes

After performing the fit the Jupyter display is updated.

load_data(data)[source]

Load a dataset into the Motofit instance.

Parameters

data (refnx.dataset.Data1D, or str, or file-like) –

load_model(*args, f=None)[source]

Load a serialised model. If f is not specified then an attempt will be made to find a model corresponding to the current dataset name, ‘model_’ + self.dataset.name + ‘.pkl’. If there is no current dataset then the most recent model will be loaded. This method is only intended to be used to deserialise models created by this interactive Jupyter widget modeller, and will not successfully load complicated ReflectModel created outside of the interactive modeller.

Parameters

f (file like or str, optional) – pickle file to load model from.

redraw(change)[source]

Redraw the Jupyter GUI associated with the Motofit instance.

save_model(*args, f=None)[source]

Serialise a model to a pickle file. If f is not specified then the file name is constructed from the current dataset name; if there is no current dataset then the filename is constructed from the current time. These constructed filenames will be in the current working directory, for a specific save location f must be provided. This method is only intended to be used to serialise models created by this interactive Jupyter widget modeller.

Parameters

f (file like or str, optional) – File to save model to.

set_model(model)[source]

Change the refnx.reflect.ReflectModel associated with the Motofit instance.

Parameters

model (refnx.reflect.ReflectModel) –

update_model(change)[source]

Updates the plots when the parameters change

Parameters

change

class refnx.reflect.ReflectModel(structure, scale=1, bkg=1e-07, name='', dq=5.0, threads=-1, quad_order=17, dq_type='pointwise', q_offset=0)[source]

Bases: object

Parameters
  • structure (refnx.reflect.Structure) – The interfacial structure.

  • scale (float or refnx.analysis.Parameter, optional) – scale factor. All model values are multiplied by this value before the background is added. This is turned into a Parameter during the construction of this object.

  • bkg (float or refnx.analysis.Parameter, optional) – Q-independent constant background added to all model values. This is turned into a Parameter during the construction of this object.

  • name (str, optional) – Name of the Model

  • dq (float or refnx.analysis.Parameter, optional) –

    • dq == 0 then no resolution smearing is employed.

    • dq is a float or refnx.analysis.Parameter

      a constant dQ/Q resolution smearing is employed. For 5% resolution smearing supply 5.

    This value is turned into a Parameter during the construction of this object.

  • threads (int, optional) – Specifies the number of threads for parallel calculation. This option is only applicable if you are using the _creflect module. The option is ignored if using the pure python calculator, _reflect. If threads == -1 then all available processors are used.

  • quad_order (int, optional) – the order of the Gaussian quadrature polynomial for doing the resolution smearing. default = 17. Don’t choose less than 13. If quad_order == ‘ultimate’ then adaptive quadrature is used. Adaptive quadrature will always work, but takes a _long_ time (2 or 3 orders of magnitude longer). Fixed quadrature will always take a lot less time. BUT it won’t necessarily work across all samples. For example, 13 points may be fine for a thin layer, but will be atrocious at describing a multilayer with bragg peaks.

  • dq_type ({'pointwise', 'constant'}, optional) – Chooses whether pointwise or constant dQ/Q resolution smearing (see dq keyword) is used. To use pointwise smearing the x_err keyword provided to Objective.model method must be an array, otherwise the smearing falls back to ‘constant’.

  • q_offset (float or refnx.analysis.Parameter, optional) – Compensates for uncertainties in the angle at which the measurement is performed. A positive/negative q_offset corresponds to a situation where the measured q values (incident angle) may have been under/over estimated, and has the effect of shifting the calculated model to lower/higher effective q values.

__call__(x, p=None, x_err=None)[source]

Calculate the generative model

Parameters
  • x (float or np.ndarray) – q values for the calculation. Units = Angstrom**-1

  • p (refnx.analysis.Parameters, optional) – parameters required to calculate the model

  • x_err (np.ndarray) – dq resolution smearing values for the dataset being considered.

Returns

reflectivity – Calculated reflectivity

Return type

np.ndarray

property bkg

refnx.analysis.Parameter - linear background added to all model values.

property dq

refnx.analysis.Parameter

  • dq.value == 0

    no resolution smearing is employed.

  • dq.value > 0

    a constant dQ/Q resolution smearing is employed. For 5% resolution smearing supply 5. However, if x_err is supplied to the model method, then that overrides any setting reported here.

logp()[source]

Additional log-probability terms for the reflectivity model. Do not include log-probability terms for model parameters, these are automatically included elsewhere.

Returns

logp – log-probability of structure.

Return type

float

model(x, p=None, x_err=None)[source]

Calculate the reflectivity of this model

Parameters
  • x (float or np.ndarray) – q values for the calculation. Units = Angstrom**-1

  • p (refnx.analysis.Parameters, optional) – parameters required to calculate the model

  • x_err (np.ndarray) – dq resolution smearing values for the dataset being considered.

Returns

reflectivity – Calculated reflectivity

Return type

np.ndarray

property parameters

refnx.analysis.Parameters - parameters associated with this model.

property q_offset

refnx.analysis.Parameter - compensates for any angular misalignment during an experiment.

property scale

refnx.analysis.Parameter - all model values are multiplied by this value before the background is added.

property structure

refnx.reflect.Structure - object describing the interface of a reflectometry sample.

class refnx.reflect.ReflectModelTL(structure, scale=1, bkg=1e-07, name='', dq=5.0, threads=-1, quad_order=17, dq_type='pointwise', t_offset=0)[source]

Bases: ReflectModel

Calculates reflectivity using angle-of-incidence/wavelength.

In most circumstances the use of ReflectModel is preferred, which works with momentum transfer. However, for some wavelength dispersive experiments the scattering length density profile (SLD) can be wavelength dependent. This is more common for X-ray reflectometry than with neutrons. This class deals with wavelength dependent SLD profiles. It will be slower than using ReflectModel. There is no point in using this class if there are no wavelength dependent Scatterers contained within the system.

Parameters
  • structure (refnx.reflect.Structure) – The interfacial structure. Should contain at least one wavelength dependent Scatterer, otherwise use of ReflectModel is preferred.

  • scale (float or refnx.analysis.Parameter, optional) – scale factor. All model values are multiplied by this value before the background is added. This is turned into a Parameter during the construction of this object.

  • bkg (float or refnx.analysis.Parameter, optional) – Q-independent constant background added to all model values. This is turned into a Parameter during the construction of this object.

  • name (str, optional) – Name of the Model

  • dq (float or refnx.analysis.Parameter, optional) –

    • dq == 0 then no resolution smearing is employed.

    • dq is a float or refnx.analysis.Parameter

      a constant dQ/Q resolution smearing is employed. For 5% resolution smearing supply 5.

    This value is turned into a Parameter during the construction of this object.

  • threads (int, optional) – Specifies the number of threads for parallel calculation. This option is only applicable if you are using the _creflect module. The option is ignored if using the pure python calculator, _reflect. If threads == -1 then all available processors are used.

  • quad_order (int, optional) – the order of the Gaussian quadrature polynomial for doing the resolution smearing. default = 17. Don’t choose less than 13. If quad_order == ‘ultimate’ then adaptive quadrature is used. Adaptive quadrature will always work, but takes a _long_ time (2 or 3 orders of magnitude longer). Fixed quadrature will always take a lot less time. BUT it won’t necessarily work across all samples. For example, 13 points may be fine for a thin layer, but will be atrocious at describing a multilayer with bragg peaks.

  • dq_type ({'pointwise', 'constant'}, optional) – Chooses whether pointwise or constant dQ/Q resolution smearing (see dq keyword) is used. To use pointwise smearing the x_err keyword provided to Objective.model method must be an array, otherwise the smearing falls back to ‘constant’.

  • t_offset (float or refnx.analysis.Parameter, optional) – Compensates for uncertainties in the angle at which the measurement is performed. A positive/negative t_offset corresponds to a situation where the measured t values (incident angle) may have been under/over estimated, and has the effect of shifting the calculated model to lower/higher effective q values.

Example

>>> from refnx.reflect import MaterialSLD, SLD, ReflectModelTL
>>> air = SLD(0)
>>> si = SLD(2.07)
>>> gd2o3 = MaterialSLD("Gd2O3", 7.41)  # wavelength dependent Scatterer
>>> s = air | gd2o3(50, 3) | si
>>> model = ReflectModelTL(s)
>>> t = [0.65] * 60    # angle of incidence
>>> l = np.geomspace(2, 20, 60)  # wavelength
>>> model(np.c_[t, l])   # calculate reflectivity
__annotations__ = {}
model(x, p=None, x_err=None)[source]

Calculate the reflectivity of this model

Parameters
  • x ((float, float) or np.ndarray) – angle of incidence/wavelength values for the calculation. If an array x should have shape (N, 2), where the first column of the N datapoints corresponds to angle of incidence (degrees) and the second column corresponds to their wavelength (angstrom**-1).

  • p (refnx.analysis.Parameters, optional) – parameters required to calculate the model

  • x_err (np.ndarray) – dq resolution smearing values for the dataset being considered.

Returns

reflectivity – Calculated reflectivity

Return type

np.ndarray

property q_offset

refnx.analysis.Parameter - compensates for any angular misalignment during an experiment.

property structure

refnx.reflect.Structure - object describing the interface of a reflectometry sample.

property t_offset

refnx.analysis.Parameter - compensates for any angular misalignment during an experiment.

class refnx.reflect.SLD(value, name='')[source]

Bases: Scatterer

Object representing freely varying SLD of a material

Parameters

Notes

An SLD object can be used to create a Slab:

>>> # an SLD object representing Silicon Dioxide
>>> sio2 = SLD(3.47, name='SiO2')
>>> # create a Slab of SiO2 20 A in thickness, with a 3 A roughness
>>> sio2_layer = sio2(20, 3)

The SLD object can also be made from a complex number, or from Parameters

>>> sio2 = SLD(3.47+0.01j)
>>> re = Parameter(3.47)
>>> im = Parameter(0.01)
>>> sio2 = SLD(re)
>>> sio2 = SLD([re, im])
__annotations__ = {}
__complex__()[source]
property parameters

refnx.analysis.Parameters associated with this component

class refnx.reflect.Sinusoidal[source]

Bases: Interface

A sinusoidal (sin) interfacial profile

Notes

Stearns, D. G. J. Appl. Phys., 1989, 65, 491–506.

__annotations__ = {}
__call__(z, scale=1, loc=0)[source]

Call self as a function.

class refnx.reflect.Slab(thick, sld, rough, name='', vfsolv=0, interface=None)[source]

Bases: Component

A slab component has uniform SLD over its thickness.

Parameters
  • thick (refnx.analysis.Parameter or float) – thickness of slab (Angstrom)

  • sld (refnx.reflect.Scatterer, complex, or float) – (complex) SLD of film (/1e-6 Angstrom**-2)

  • rough (refnx.analysis.Parameter or float) – roughness on top of this slab (Angstrom)

  • name (str) – Name of this slab

  • vfsolv (refnx.analysis.Parameter or float) – Volume fraction of solvent [0, 1]

  • interface ({Interface, None}, optional) – The type of interfacial roughness associated with the Slab. If None, then the default interfacial roughness is an Error function (also known as Gaussian roughness).

__annotations__ = {}
__str__()[source]

Return str(self).

property parameters

refnx.analysis.Parameters associated with this component

slabs(structure=None)[source]

Slab representation of this component. See Component.slabs

class refnx.reflect.SpinChannel(value)[source]

Bases: Enum

Describes the incident and scattered spin state of a polarised neutron beam.

DOWN_DOWN = (0, 0)
DOWN_UP = (0, 1)
UP_DOWN = (1, 0)
UP_UP = (1, 1)
class refnx.reflect.Spline(extent, vs, dz, name='', interpolator=<class 'scipy.interpolate._cubic.PchipInterpolator'>, zgrad=True, microslab_max_thickness=1)[source]

Bases: Component

Freeform modelling of the real part of an SLD profile using spline interpolation.

Parameters
  • extent (float or Parameter) – Total extent of spline region

  • vs (Sequence of float/Parameter) – the real part of the SLD values of each of the knots.

  • dz (Sequence of float/Parameter) – the lateral offset between successive knots.

  • name (str) – Name of component

  • interpolator (scipy.interpolate Univariate Interpolator, optional) – Which scipy.interpolate Univariate Interpolator to use.

  • zgrad (bool, optional) – If true then extra control knots are placed outside this spline with the same SLD as the materials on the left and right. With a monotonic interpolator this guarantees that the gradient is zero at either end of the interval.

  • microslab_max_thickness (float) – Maximum size of the microslabs approximating the spline.

Notes

This spline component only generates the real part of the SLD (thereby assuming that the imaginary part is negligible). The sequence dz are the lateral offsets of the knots normalised to a unit interval [0, 1]. The reason for using lateral offsets is so that the knots are monotonically increasing in location. When each dz offset is turned into a Parameter it is given bounds in [0, 1]. Thus with an extent of 500, and dz = [0.1, 0.2, 0.2], the knots will be at [0, 50, 150, 250, 500]. Notice that there are two extra knots for the start and end of the interval (disregarding the zgrad control knots). If np.sum(dz) > 1, then the knot spacings are normalised to 1. e.g. dz of [0.1, 0.2, 0.9] would result in knots (in the normalised interval) of [0, 0.0833, 0.25, 1, 1]. If vs is monotonic then the output spline will be monotonic. If vs is not monotonic then there may be regions of the spline larger or smaller than left or right. The slab representation of this component are approximated using a ‘microslab’ representation of spline. The max thickness of each microslab is microslab_max_thickness.

A Spline component should not be used more than once in a given Structure.

__annotations__ = {}
__call__(z, structure)[source]

Calculates the spline value at z

Parameters
Returns

sld – Real part of SLD

Return type

float

logp()[source]

The log-probability that this Component adds to the total log-prior term. Do not include log-probability terms for the actual parameters, these are automatically included elsewhere.

Returns

logp – Log-probability

Return type

float

property parameters

refnx.analysis.Parameters associated with this component

slabs(structure=None)[source]

Slab representation of the spline, as an array

Parameters

structure (refnx.reflect.Structure) – The Structure hosting this Component

class refnx.reflect.Stack(components=(), name='', repeats=1)[source]

Bases: Component, UserList

A series of Components to be considered as one. When part of a Structure the Stack can represent a multilayer by setting the repeats attribute.

Parameters
  • components (sequence) – A series of Components to initialise the stack with

  • name (str) – Name of the Stack

  • repeats (number, Parameter) – When viewed from a parent Structure the Components in this Stack will appear to be repeated repeats times. Internally repeats is rounded to the nearest integer before use, allowing it to be used as a fitting parameter.

Notes

To add Components to the Stack you can:

  • initialise the object with a list of Components

  • utilise list methods (extend, append, insert, etc)

  • Add by __ior__ (e.g. stack |= component)

You can’t use __or__ to add Components to a stack (e.g. Stack() | component) ORing a Stack with other Components will make a Structure.

__annotations__ = {}
__ior__(other)[source]

Build a Stack by IOR’ing.

Parameters

other (Component, Scatterer) – The object to add to the structure.

__setitem__(i, v)[source]
__str__()[source]

Return str(self).

append(item)[source]

Append a Component to the Stack.

Parameters

item (refnx.reflect.Component) – The component to be added.

property components

The list of components in the sample.

property interfaces

The interfacial roughness type between each layer in Component.slabs. Should be one of {None, Interface, or sequence of Interface}.

property parameters

refnx.analysis.Parameters, all the parameters associated with this structure.

slabs(structure=None)[source]

Slab representation of this component. See Component.slabs

Notes

The overall set of slabs returned by this method consists of the concatenated constituent Component slabs repeated Stack.repeats times.

class refnx.reflect.Step[source]

Bases: Interface

A step function interfacial profile

Notes

Svechnikov, M.; Pariev, D.; Nechay, A.; Salashchenko, N.; Chkhalo, N.; Vainer, Y. & Gaman, D., “Extended model for the reconstruction of periodic multilayers from extreme ultraviolet and X-ray reflectivity data”, Journal of Applied Crystallography, 2017, 50, 1428-1440

__annotations__ = {}
__call__(z, scale=1, loc=0)[source]

Call self as a function.

class refnx.reflect.Structure(components=(), name='', solvent=None, reverse_structure=False, contract=0, wavelength=None)[source]

Bases: UserList

Represents the interfacial Structure of a reflectometry sample. Successive Components are added to the Structure to construct the interface.

Parameters
  • components (sequence) – A sequence of Components to initialise the Structure.

  • name (str) – Name of this structure

  • solvent (refnx.reflect.Scatterer) – Specifies the scattering length density used for solvation. If no solvent is specified then the SLD of the solvent is assumed to be the SLD of Structure[-1].slabs()[-1] (after any possible slab order reversal).

  • reverse_structure (bool) – If Structure.reverse_structure is True then the slab representation produced by Structure.slabs is reversed. The sld profile and calculated reflectivity will correspond to this reversed structure.

  • contract (float) – If contract > 0 then an attempt to contract/shrink the slab representation is made. Use larger values for coarser profiles (and vice versa). A typical starting value to try might be 1.0.

  • wavelength (float, None) – Wavelength the sample was measured at.

Notes

If Structure.reverse_structure is True then the slab representation order is reversed. If no solvent is specified then the volume fraction of solvent in each of the Components is assumed to have the scattering length density of Structure[-1].slabs()[-1] after any possible slab order reversal. This slab corresponds to the scattering length density of the semi-infinite backing medium. Normally the reflectivity will be calculated using the Nevot-Croce approximation for Gaussian roughness between different layers. However, if individual components have non-Gaussian roughness (e.g. Tanh), then the overall reflectivity and SLD profile are calculated by micro-slicing. Micro-slicing involves calculating the specific SLD profile, dividing it up into small-slabs, and calculating the reflectivity from those. This normally takes much longer than the Nevot-Croce approximation. To speed the calculation up the Structure.contract property can be used. Contracting too far may mask the subtle differences between different roughness types. The profile contraction specified by this property can greatly improve calculation time for Structures created with micro-slicing. If you use this option it is recommended to check the reflectivity signal with and without contraction to ensure they are comparable.

Example

>>> from refnx.reflect import SLD, Linear, Tanh, Interface
>>> # make the materials
>>> air = SLD(0, 0)
>>> # overall SLD of polymer is (1.0 + 0.001j) x 10**-6 A**-2
>>> polymer = SLD(1.0 + 0.0001j)
>>> si = SLD(2.07)
>>> # Make the structure, s, from slabs.
>>> # The polymer slab has a thickness of 200 A and a air/polymer roughness
>>> # of 4 A.
>>> s = air(0, 0) | polymer(200, 4) | si(0, 3)

Use Linear roughness between air and polymer (rather than default Gaussian roughness). Use Tanh roughness between si and polymer. If non-default roughness is used then the reflectivity is calculated via micro-slicing - set the contract property to speed the calculation up.

>>> s[1].interfaces = Linear()
>>> s[2].interfaces = Tanh()
>>> s.contract = 0.5

Create a user defined interfacial roughness based on the cumulative distribution function (CDF) of a Cauchy.

>>> from scipy.stats import cauchy
>>> class Cauchy(Interface):
...     def __call__(self, x, loc=0, scale=1):
...         return cauchy.cdf(x, loc=loc, scale=scale)
>>>
>>> c = Cauchy()
>>> s[1].interfaces = c
__annotations__ = {}
__ior__(other)[source]

Build a structure by IOR’ing Structures/Components/SLDs.

Parameters

other (Structure, Component, SLD) – The object to add to the structure.

Examples

>>> air = SLD(0, name='air')
>>> sio2 = SLD(3.47, name='SiO2')
>>> si = SLD(2.07, name='Si')
>>> structure = air | sio2(20, 3)
>>> structure |= si(0, 4)
__or__(other)[source]

Build a structure by OR’ing Structures/Components/SLDs.

Parameters

other (Structure, Component, SLD) – The object to add to the structure.

Examples

>>> air = SLD(0, name='air')
>>> sio2 = SLD(3.47, name='SiO2')
>>> si = SLD(2.07, name='Si')
>>> structure = Structure()
>>> structure = air | sio2(20, 3) | si(0, 3)
__setitem__(i, v)[source]
__str__()[source]

Return str(self).

append(item)[source]

Append a Component to the Structure.

Parameters

item (refnx.reflect.Component) – The component to be added.

property components

The list of components in the sample.

contract

float if contract > 0 then an attempt to contract/shrink the slab representation is made. Use larger values for coarser profiles (and vice versa). A typical starting value to try might be 1.0.

classmethod from_slabs(slabs)[source]
property interfaces

A nested list containing the interfacial roughness types for each of the Component`s. `len(Structure.interfaces) == len(Structure.components)

logp()[source]

log-probability for the interfacial structure. Note that if a given component is present more than once in a Structure then it’s log-prob will be counted twice.

Returns

logp – log-prior for the Structure.

Return type

float

property name
overall_sld(slabs, solvent)[source]

Performs a volume fraction weighted average of the material SLD in a layer and the solvent in a layer.

Parameters
  • slabs (np.ndarray) – Slab representation of the layers to be averaged.

  • solvent (complex or reflect.Scatterer) – SLD of solvating material.

Returns

averaged_slabs – the averaged slabs.

Return type

np.ndarray

property parameters

refnx.analysis.Parameters, all the parameters associated with this structure.

plot(pvals=None, samples=0, fig=None, align=0)[source]

Plot the structure.

Requires matplotlib be installed.

Parameters
  • pvals (np.ndarray, optional) – Numeric values for the Parameter’s that are varying

  • samples (number) – If this structures constituent parameters have been sampled, how many samples you wish to plot on the graph.

  • fig (Figure instance, optional) – If fig is not supplied then a new figure is created. Otherwise the graph is created on the current axes on the supplied figure.

  • align (int, optional) – Aligns the plotted structures around a specified interface in the slab representation of a Structure. This interface will appear at z = 0 in the sld plot. Note that Components can consist of more than a single slab, so some thought is required if the interface to be aligned around lies in the middle of a Component. Python indexing is allowed, e.g. supplying -1 will align at the backing medium.

Returns

fig, axmatplotlib figure and axes objects.

Return type

matplotlib.Figure, matplotlib.Axes

reflectivity(q, threads=0)[source]

Calculate theoretical reflectivity of this structure

Parameters
  • q (array-like) – Q values (Angstrom**-1) for evaluation

  • threads (int, optional) – Specifies the number of threads for parallel calculation. This option is only applicable if you are using the _creflect module. The option is ignored if using the pure python calculator, _reflect. If threads == 0 then all available processors are used.

Notes

Normally the reflectivity will be calculated using the Nevot-Croce approximation for Gaussian roughness between different layers. However, if individual components have non-Gaussian roughness (e.g. Tanh), then the overall reflectivity and SLD profile are calculated by micro-slicing. Micro-slicing involves calculating the specific SLD profile, dividing it up into small-slabs, and calculating the reflectivity from those. This normally takes much longer than the Nevot-Croce approximation. To speed the calculation up the Structure.contract property can be used.

property reverse_structure

bool if True then the slab representation produced by Structure.slabs is reversed. The sld profile and calculated reflectivity will correspond to this reversed structure.

slabs(**kwds)[source]
Returns

slabs – Slab representation of this structure. Has shape (N, 5).

  • slab[N, 0]

    thickness of layer N

  • slab[N, 1]

    overall SLD.real of layer N (material AND solvent)

  • slab[N, 2]

    overall SLD.imag of layer N (material AND solvent)

  • slab[N, 3]

    roughness between layer N and N-1

  • slab[N, 4]

    volume fraction of solvent in layer N.

Return type

np.ndarray

Notes

If Structure.reversed is True then the slab representation order is reversed. The slab order is reversed before the solvation calculation is done. I.e. if Structure.solvent == ‘backing’ and Structure.reversed is True then the material that solvates the system is the component in Structure[0], which corresponds to Structure.slab[-1].

sld_profile(z=None, align=0, max_delta_z=None)[source]

Calculates an SLD profile, as a function of distance through the interface.

Parameters
  • z (float) – Interfacial distance (Angstrom) measured from interface between the fronting medium and the first layer.

  • align (int, optional) – Places a specified interface in the slab representation of a Structure at z = 0. Python indexing is allowed, e.g. supplying -1 will place the backing medium at z = 0.

  • max_delta_z ({None, float}, optional) – If specified this will control the maximum spacing between SLD points. Only used if z is None.

Returns

sld – Scattering length density / 1e-6 Angstrom**-2

Return type

float

Notes

This can be called in vectorised fashion.

property solvent
class refnx.reflect.Tanh[source]

Bases: Interface

A hyperbolic tangent (tanh) interfacial profile

Notes

D. Bahr; W. Press; R. Jebasinski; S. Mantl, Phys. Rev. B,1993, 47 (8), 4385

__annotations__ = {}
__call__(z, scale=1, loc=0)[source]

Call self as a function.

refnx.reflect.abeles(x, w, scale=1.0, bkg=0.0, threads=-1)

Abeles matrix formalism for calculating reflectivity from a stratified medium.

Parameters
  • q (array_like) – the q values required for the calculation. Q = 4 * Pi / lambda * sin(omega). Units = Angstrom**-1

  • layers (np.ndarray) – coefficients required for the calculation, has shape (2 + N, 4), where N is the number of layers layers[0, 1] - SLD of fronting (/1e-6 Angstrom**-2) layers[0, 2] - iSLD of fronting (/1e-6 Angstrom**-2) layers[N, 0] - thickness of layer N layers[N, 1] - SLD of layer N (/1e-6 Angstrom**-2) layers[N, 2] - iSLD of layer N (/1e-6 Angstrom**-2) layers[N, 3] - roughness between layer N-1/N layers[-1, 1] - SLD of backing (/1e-6 Angstrom**-2) layers[-1, 2] - iSLD of backing (/1e-6 Angstrom**-2) layers[-1, 3] - roughness between backing and last layer

  • scale (float) – Multiply all reflectivities by this value.

  • bkg (float) – Linear background to be added to all reflectivities

  • threads (int, optional) – How many threads you would like to use in the reflectivity calculation. If threads == -1 then the calculation is automatically spread over multiprocessing.cpu_count() threads.

Returns

Reflectivity – Calculated reflectivity values for each q value.

Return type

np.ndarray

refnx.reflect.available_backends()[source]

tuple containing the available reflectivity calculator backends

refnx.reflect.choose_dq_type(objective)[source]

Chooses which resolution smearing approach has the fastest calculation time.

Parameters

objective (Objective) – The objective being calculated

Returns

method – One of {‘pointwise’, ‘constant’}. If ‘pointwise’ then using the resolution information from the datafile is the fastest mode of calculation. If ‘constant’, then a constant dq/q (expressed as a percentage) Q resolution is quicker.

Return type

str

refnx.reflect.gui(expt_file=None)[source]
refnx.reflect.main(args=None)[source]
refnx.reflect.reflectivity(q, slabs, scale=1.0, bkg=0.0, dq=5.0, quad_order=17, threads=-1, q_offset=0)[source]

Abeles/Parratt formalism for calculating reflectivity from a stratified medium.

Parameters
  • q (np.ndarray) – The qvalues required for the calculation. \(Q=\frac{4Pi}{\lambda}\sin(\Omega)\). Units = Angstrom**-1

  • slabs (np.ndarray) –

    coefficients required for the calculation, has shape (2 + N, 4), where N is the number of layers

    • slabs[0, 0]

      ignored

    • slabs[N, 0]

      thickness of layer N

    • slabs[N+1, 0]

      ignored

    • slabs[0, 1]

      SLD_real of fronting (/1e-6 Angstrom**-2)

    • slabs[N, 1]

      SLD_real of layer N (/1e-6 Angstrom**-2)

    • slabs[-1, 1]

      SLD_real of backing (/1e-6 Angstrom**-2)

    • slabs[0, 2]

      SLD_imag of fronting (/1e-6 Angstrom**-2)

    • slabs[N, 2]

      iSLD_imag of layer N (/1e-6 Angstrom**-2)

    • slabs[-1, 2]

      iSLD_imag of backing (/1e-6 Angstrom**-2)

    • slabs[0, 3]

      ignored

    • slabs[N, 3]

      roughness between layer N-1/N

    • slabs[-1, 3]

      roughness between backing and layer N

  • scale (float) – scale factor. All model values are multiplied by this value before the background is added

  • bkg (float) – Q-independent constant background added to all model values.

  • dq (float or np.ndarray, optional) –

    • dq == 0

      no resolution smearing is employed.

    • dq is a float

      a constant dQ/Q resolution smearing is employed. For 5% resolution smearing supply 5.

    • dq is the same shape as q

      the array contains the FWHM of a Gaussian approximated resolution kernel. Point by point resolution smearing is employed. Use this option if dQ/Q varies across your dataset.

    • dq.ndim == q.ndim + 2 and q.shape == dq[…, -3].shape

      an individual resolution kernel is applied to each measurement point. This resolution kernel is a probability distribution function (PDF). dq will have the shape (qvals.shape, 2, M). There are M points in the kernel. dq[:, 0, :] holds the q values for the kernel, dq[:, 1, :] gives the corresponding probability.

  • quad_order (int, optional) – the order of the Gaussian quadrature polynomial for doing the resolution smearing. default = 17. Don’t choose less than 13. If quad_order == ‘ultimate’ then adaptive quadrature is used. Adaptive quadrature will always work, but takes a _long_ time (2 or 3 orders of magnitude longer). Fixed quadrature will always take a lot less time. BUT it won’t necessarily work across all samples. For example, 13 points may be fine for a thin layer, but will be atrocious at describing a multilayer with bragg peaks.

  • threads (int, optional) – Specifies the number of threads for parallel calculation. This option is only applicable if you are using the _creflect module. The option is ignored if using the pure python calculator, _reflect. If threads == -1 then all available processors are used.

  • q_offset (float or refnx.analysis.Parameter, optional) – Compensates for uncertainties in the angle at which the measurement is performed. A positive/negative q_offset corresponds to a situation where the measured q values (incident angle) may have been under/over estimated, and has the effect of shifting the calculated model to lower/higher effective q values.

Example

>>> from refnx.reflect import reflectivity
>>> q = np.linspace(0.01, 0.5, 1000)
>>> slabs = np.array([[0, 2.07, 0, 0],
...                   [100, 3.47, 0, 3],
...                   [500, -0.5, 0.00001, 3],
...                   [0, 6.36, 0, 3]])
>>> print(reflectivity(q, slabs))
refnx.reflect.sld_profile(slabs, z=None, max_delta_z=None)[source]

Calculates an SLD profile, as a function of distance through the interface.

Parameters
  • slabs (np.ndarray) –

    Slab representation of this structure. Has shape (N, 5).

    • slab[N, 0]

      thickness of layer N

    • slab[N, 1]

      overall SLD.real of layer N (material AND solvent)

    • slab[N, 2]

      overall SLD.imag of layer N (material AND solvent)

    • slab[N, 3]

      roughness between layer N and N-1

    • slab[N, 4]

      volume fraction of solvent in layer N, ignored for this function

  • z ({None, np.ndarray}, optional) – If z is None then the SLD profile will have 500 points (unless max_delta_z is specified). If z is an array, then the array specifies the interfacial locations at which the SLD will be evaluated.

  • max_delta_z ({None, float}, optional) – If specified this will control the maximum spacing between SLD points. Only used if z is None.

Returns

sld – Scattering length density / 1e-6 Angstrom**-2

Return type

float

Notes

This can be called in vectorised fashion.

refnx.reflect.use_reflect_backend(backend='c')[source]

Context manager for temporarily setting the backend used for calculating reflectivity

Parameters

backend ({'python', 'cython', 'c', 'pyopencl', 'py_parratt', 'c_parratt',) – ‘numba_parratt’}, str The function that calculates the reflectivity. Speed should go in the order: numba_parratt > c_parratt > c > pyopencl / cython > python. If a particular method is not available the function falls back to another option.

Yields

kernel (callable) – A callable that calculates the reflectivity

Notes

‘c’ is preferred for most circumstances, because it’s pretty much guaranteed to be present. ‘pyopencl’ uses a GPU to calculate reflectivity and requires that pyopencl be installed. It may not as accurate as the other options. ‘pyopencl’ is only included for completeness. The ‘pyopencl’ backend is also harder to use with multiprocessing-based parallelism.