pyextal.optimize¶
Attributes¶
Classes¶
Class for coarse optimization of thickness, orientation, and gl. |
|
Class for fine optimization of the structure factor. |
Functions¶
|
Chooses which reflections a display method draws. |
|
Lays out |
|
Generates a 2D Voigt profile. |
Module Contents¶
- pyextal.optimize.MAX_PANELS = 24¶
- pyextal.optimize.PANEL_COLS = 8¶
- pyextal.optimize.selectBeams(gInclude, beams=None, maxPanels=MAX_PANELS)¶
Chooses which reflections a display method draws.
- Parameters:
gInclude (Sequence) – The ROI’s reflections, in template order.
beams (Sequence | str, optional) – Positions in
gIncludeand/or(h, k, l)tuples to draw, or'all'. Defaults to None, the firstmaxPanelsreflections.maxPanels (int, optional) – Cap applied when
beamsis None. Defaults to MAX_PANELS.
- Returns:
Positions in
gInclude.- Return type:
List[int]
- pyextal.optimize.panelGrid(npanels, rowsPerPanel=1, ncols=PANEL_COLS, size=(3.0, 3.0))¶
Lays out
npanelspanels on a wrapped grid.- Parameters:
npanels (int) – Number of panels.
rowsPerPanel (int, optional) – Axes stacked vertically per panel, e.g. 2 for an experiment-over-simulation pair. Defaults to 1.
ncols (int, optional) – Panels per row. Defaults to PANEL_COLS.
size (tuple, optional) – (width, height) in inches of one axes.
- Returns:
(fig, panels)wherepanels[p]is the list ofrowsPerPanelaxes of panelp. Unused grid cells are removed.- Return type:
tuple
- class pyextal.optimize.CoarseOptimize(dinfo: pyextal.dinfo.BaseDiffractionInfo, roi: pyextal.roi.BaseROI, searchRadius: float = None, nx: int = None, backend: str = 'numpy')¶
Class for coarse optimization of thickness, orientation, and gl.
- Variables:
dinfo (BaseDiffractionInfo) – Diffraction information object.
param (SimParams) – Bloch simulation from dinfo.
roi (BaseROI) – The region of interest object.
thickness (float) – The sample thickness from dinfo.
gl (float) – geometric scaling factor from dinfo.
indices (List[int]) – List of indices matching reflections to the exitwave.
exitwave (np.ndarray) – The simulated exitwave.
side (float) – The side length of the simulation used for tilt mapping.
scale_factor (float) – The scale factor from LARBED calibration between simulation and experiment.
templates (np.ndarray) – The experimental templates extracted from the ROI.
- dinfo¶
- backend = 'numpy'¶
- param¶
- roi¶
- thickness¶
- gl¶
- indices = []¶
- exitwave¶
- templates¶
- correlate(exitwave, templates, margin=2)¶
Cross-correlates a simulation against the experimental templates.
The full search covers every offset of the templates within the zoomed simulation – on the SrTiO3 example a 459x459 space, and 56% of the cost of one temperature-factor evaluation. Once the orientation is known, re-searching all of it to re-find the same peak is wasted work, so setting
searchWindowrestricts the search to a box around the previous peak.- Parameters:
exitwave (np.ndarray) – (nbeam, ny, nx) zoomed simulation.
templates (np.ndarray) – (nbeam, ty, tx) experimental templates.
margin (int, optional) – How close to a window edge a peak may sit before the window is judged too small. Defaults to 2.
- Returns:
(total, origin)– the correlation volume and the(row, col)offset of its origin within the full search space, so a peak position maps back asloc + origin.- Return type:
tuple
Note
searchWindowdefaults to None, the full search, which is what every caller gets unless it opts in.The window is only trusted when its peak sits away from an edge that the full search would have seen past. An edge that coincides with the edge of the whole search space is not suspicious – on the SrTiO3 example the peak really does sit in column 0 – but an interior one means the true peak may lie outside, and the full search is repeated. The check lives here rather than in the caller because
thicknessTargetreads this correlation too: a window that silently clipped the peak would corrupt every value in the inner thickness search, and no later check could undo that.
- optimizeOrientationGeometry(target: Callable, targetValue: float) float¶
Optimizes a single parameter (thickness or gl) and the sample orientation.
This method uses scipy.optimize.minimize_scalar to find the optimal value for a given target function (e.g., thickness or gl). After finding the best parameter value, it determines the optimal sample tilt by finding the location of the maximum correlation in the template matching result.
- Parameters:
target (Callable) – The target function to minimize (e.g., thicknessTarget or glTarget).
targetValue (float) – The initial guess for the parameter being optimized.
- Returns:
The optimized value for the target parameter.
- Return type:
float
- optimizeOrientationThickness(filter=None, threshold=None) None¶
Optimizes the thickness and orientation of the experimental pattern.
- optimizeOrientationGL(filter=None, threshold=None) None¶
Optimizes the gl and orientation of the experimental pattern.
- static thicknessTarget(x0, *args)¶
Error function for thickness optimization.
- Parameters:
x0 (float) – Thickness value.
*args – CoarseOptimize instance.
- Returns:
The optimization error, calculated as 1 - max_correlation.
- Return type:
float
- static glTarget(x0, *args)¶
Error function for gl optimization.
- Parameters:
x0 (float) – gl value.
*args – CoarseOptimize instance.
- Returns:
The optimization error, calculated as 1 - max_correlation.
- Return type:
float
- optimizeDWF(aniso=False, group='atom', method=None, options=None, refit_xtol=None, window=None, verbose=True) None¶
Optimizes the temperature factors against the cross-correlation.
Each evaluation costs a full re-diagonalization – the temperature factors enter
Ugh, so there is no way to avoidbloch_run– plus the inner thickness/orientation refit that keeps the comparison fair. Everything here is therefore aimed at needing fewer evaluations and making each one cheaper, rather than at the search itself.- Parameters:
aniso (bool, optional) – Refine the symmetry-allowed anisotropic components of each site instead of one isotropic B. The number of parameters is set by site symmetry, not by hand: see
pyextal.adp.allowed_beta_basis(). Defaults to False.group (str | list, optional) –
'atom'for one parameter set per asymmetric-unit atom,'type'to tie atoms of the same element together, or an explicit list of index lists. Defaults to'atom'.method (str, optional) – scipy solver. Defaults to
constant['coarse_DWF']['method'].options (dict, optional) – scipy solver options. Defaults to
constant['coarse_DWF']['options'], filtered to the ones the chosen solver actually accepts.refit_xtol (float, optional) – Temporarily loosens the tolerance of the inner thickness fit for the duration of the search. Brent reads it as a relative tolerance, so the configured 1e-3 is already only about half an Angstrom at a typical thickness.
window (int, optional) – Half-width, in pixels, of the correlation search box held around the known peak, via
searchWindow. Opt-in, and off by default: the full search is the largest single cost here (56% of an evaluation on the SrTiO3 example, against 15% forbloch_run), and a window of 24 px cuts an evaluation from 56 s to 25 s – but it is not free. The inner thickness fit is not bracketed, so a single evaluation can walk the thickness by 20 Angstrom, far enough for the best template offset to leave a small box, and on the SrTiO3 example that changed the first evaluation’s score from 0.31104 to 0.31362. Set it when the orientation is already converged and the speed matters, and read the drift warning printed at the end.verbose (bool, optional) – Report each evaluation. Defaults to True.
Warning
On the SrTiO3 LARBED example this target has no interior minimum.
1 - corrfalls monotonically as B(Sr) goes 0.62 -> 2.0 and every atom ends pinned against the 2.0 Angstrom^2 bound, from starting values of 0.62 / 0.44 / 0.80 – physically wrong for SrTiO3 at room temperature. The correlation prefers more thermal damping without limit, so what comes back is the bound rather than a measurement. A warning is printed when that happens. Check it before quoting any number from here, and prefer the chi-squared metrics ofFineOptimizeor the JAX stage for temperature factors.Note
The local sensitivity is tiny too – a 23% change in B(Sr) moves the objective by 5e-5 – so a tight convergence tolerance mostly buys noise on top of a target that is already pointing the wrong way.
- static _dwfOptions(method, options, n)¶
Translates the configured options into ones the solver accepts.
constant['coarse_DWF']['options']is written in Nelder-Mead spellings (fatol,xatol,adaptive) while the configured method is Powell, which discards them – so the tolerances never reached the solver and it ran on scipy’s defaults. This maps them across.- Parameters:
method (str) – scipy solver name.
options (dict) – Requested options.
n (int) – Number of free parameters.
- Returns:
Options the solver accepts.
- Return type:
dict
Note
Scaling Powell’s
direcdoes not shrink its line search here, which is worth stating because it looks like it should. Withboundsgiven,_linesearch_powelltakes the_minimize_scalar_boundedbranch and searches the whole feasible interval along each direction, so the direction’s magnitude only rescales the step variable. It does rescale the tolerance, which is measured in that variable: a smallerdirectherefore converges tighter and costs more evaluations. Control the cost withxtolandftol, which are in the units of the parameters and the objective.
- static callbackDWF(y0)¶
Prints the current parameter vector.
- Parameters:
y0 (np.ndarray) – Current parameters.
Note
Kept for callers that pass it explicitly.
optimizeDWF()reports per evaluation instead, which is the granularity that matters when one evaluation is a simulation.
- static correlationTargetDWF(y0, *args)¶
Error function for DWF optimization.
- Parameters:
y0 (np.ndarray) – Temperature-factor coefficients in the active
pyextal.adp.DWFModelparameterization. For the default isotropic per-atom refinement these are the B values, one per asymmetric-unit atom, exactly as before.*args – a CoarseOptimize instance.
- Returns:
The optimization error, calculated as 1 - max_correlation.
- Return type:
float
- optimizeXYZ() None¶
Optimizes the atomic (x, y, z) coordinates for all atoms.
This method uses scipy.optimize.minimize to find the optimal atomic positions that maximize the correlation between simulated and experimental patterns.
- static callbackXYZ(y0)¶
- static correlationTargetXYZ(y0, *args)¶
Error function for XYZ coordinate optimization.
- Parameters:
y0 (np.ndarray) – XYZ coordinates for each atom.
*args – a CoarseOptimize instance.
- Returns:
The optimization error, calculated as 1 - max_correlation.
- Return type:
float
- optimizeCell() None¶
Optimizes the cell parameters.
Currently, this method optimizes ‘a’ and ‘c’ for a tetragonal/hexagonal system, assuming a=b. It uses scipy.optimize.minimize to find the optimal cell parameters that maximize the correlation.
- static callbackCell(y0)¶
- static correlationTargetCell(y0, *args)¶
Error function for cell parameter optimization.
- Parameters:
y0 (np.ndarray) – Cell parameters.
*args – a CoarseOptimize instance.
- Returns:
The optimization error, calculated as 1 - max_correlation.
- Return type:
float
- optimizeHV(filter=None, threshold=None) None¶
Optimizes the high voltage (HV).
- static HVTarget(x0, *args)¶
Error function for HV optimization.
- Parameters:
x0 (float) – High voltage value.
*args – a CoarseOptimize instance.
- Returns:
The correlation error.
- Return type:
float
- displayCoarseSearch(filter=None, threshold=None, beams=None)¶
Displays the result of the coarse search.
- Parameters:
filter (Callable, optional) – Filter applied to both images.
threshold (Callable, optional) – Threshold applied to both images.
beams (Sequence | str, optional) – Reflections to draw, as positions in
roi.gIncludeand/or(h, k, l)tuples, or'all'. Defaults to the first MAX_PANELS.
- class pyextal.optimize.FineOptimize(dinfo: pyextal.dinfo.BaseDiffractionInfo, roi: pyextal.roi.BaseROI, reflections: List[Tuple[int, int, int]], sfMask: numpy.ndarray, noncentro: bool = False, errorFunc: pyextal.gof.BaseGOF = None, perturbROI: bool = False, shiftDisk: bool = False, symUpdate=False, probe: Tuple[float, float] = None, refineProbe: bool = True, backend: str = 'numpy')¶
Class for fine optimization of the structure factor.
- Variables:
dinfo (BaseDiffractionInfo) – The main diffraction information object.
thickness (float) – The thickness of the sample in Angstroms from dinfo.
lastParam (SimParams) – The last used simulation parameters.
roi (BaseROI) – The region of interest object for refinement.
refineProbe (bool) – Flag to indicate if probe parameters should be refined.
reflections (List[Tuple[int, int, int]]) – List of (h, k, l) Miller indices for the reflections being optimized.
sfMask (np.ndarray) – Mask to select which structure factor components to optimize.
noncentro (bool) – Flag for non-centrosymmetric structures.
errorFunc (BaseGOF) – The goodness-of-fit function used for optimization.
symUpdate (bool) – Flag to update Ugh matrix with symmetry equivalents.
history (List) – A list to store the optimization history.
- dinfo¶
- thickness¶
- lastParam¶
- roi¶
- _probe = None¶
- refineProbe = True¶
- backend = 'numpy'¶
- reflections¶
- sfMask¶
- noncentro = False¶
- errorFunc = None¶
- _perturbROI = False¶
- _shiftDisk = False¶
- symUpdate = False¶
- history = []¶
- _nfit = 0¶
- property perturbROI¶
Flag to indicate if ROI parameters (thickness, gl, rotation) should be refined.
- Type:
bool
- property probe¶
Probe parameters (sigma, gamma) for convolution.
- Type:
tuple[float, float] | None
- property shiftDisk¶
Flag to indicate if individual disk shifts should be refined.
- Type:
bool
- calDOF() int¶
Calculates the degrees of freedom for the optimization.
- Returns:
the degree of freedom for the optimization.
- Return type:
int
- getx0(x0=None) None¶
Gets the initial guess for the optimization.
- Parameters:
x0 (np.ndarray, optional) – Initial guess for structure factors. Shape (len(reflections), 4) for non-centro, (len(reflections), 2) for centro. Defaults to None.
- getRange(x0Range=None) None¶
Sets the range to normalize the structure factor.
- normalizeX0()¶
Normalizes the structure factor and applies the mask.
- denormalizeX0(x0)¶
Denormalizes the structure factor and removes the mask.
- static canBlit(canvas) bool¶
True if canvas implements the blitting API the live plot uses.
Only the Agg-derived canvases (Qt5Agg, TkAgg, Agg, …) provide copy_from_bbox/restore_region. A bare FigureCanvasBase, which is what a figure carries under some notebook backends, does not — blitting into one raises AttributeError.
- Parameters:
canvas – The figure canvas to probe.
- Returns:
True if the canvas can blit.
- Return type:
bool
- optimize(x0: numpy.ndarray = None, x0Range: numpy.ndarray = None, refineSF: bool = True, beams=None) None¶
Runs the fine optimization.
- Parameters:
x0 (np.ndarray, optional) – Initial guess for structure factors. Defaults to None.
x0Range (np.ndarray, optional) – Range for structure factor normalization. Defaults to None.
refineSF (bool, optional) – If False, the structure factors are held at x0 and only the geometry (thickness, and gl/rotation/shift, disk shifts and probe when those are enabled) is refined, by a single evaluation of SFtarget. Defaults to True.
beams (Sequence | str, optional) – Reflections drawn in the live plot, as positions in
roi.gIncludeand/or(h, k, l)tuples, or'all'. Defaults to the first MAX_PANELS; every reflection is refined either way.
- evaluateSF(x0: numpy.ndarray) None¶
Evaluates the structure factor and solve for the eigenvector/values.
- Parameters:
x0 (np.ndarray) – Structure factor values.
- evaluateParam(thickness=None)¶
Evaluates CBED intensity based on Bloch simulation results and geometry.
- Parameters:
thickness (float, optional) – Sample thickness. Defaults to None.
- Returns:
Simulated CBED pattern.
- Return type:
np.ndarray
- display(lines=(), savedir=None, beams=None, ncols=PANEL_COLS)¶
Displays the optimization result.
- Parameters:
lines (List[int], optional) – Rows of each disk to plot as line profiles. Defaults to none.
savedir (str, optional) – Directory to save the plot. Defaults to None.
beams (Sequence | str, optional) – Reflections to draw, as positions in
roi.gIncludeand/or(h, k, l)tuples, or'all'. Defaults to the first MAX_PANELS. The returned patterns always hold every reflection.ncols (int, optional) – Reflections per figure; the rest go on further figures, saved as
region_<n>_<page>.png. Defaults to PANEL_COLS.
- Returns:
- Experimental and simulated
regional patterns.
- Return type:
Tuple[List[np.ndarray], List[np.ndarray]]
- static SFtarget(x0, *args)¶
Error function for structure factor optimization.
- Parameters:
x0 (np.ndarray) – Structure factor values.
*args – Variable length argument list, expects a FineOptimize instance.
- Returns:
The optimization error.
- Return type:
float
- static ROItarget(x0, *args)¶
Error function for ROI optimization.
- Parameters:
x0 (np.ndarray) – ROI parameters (thickness, gl, rotation, allshift).
*args – a FineOptimize instance.
- Returns:
The goodness of fit.
- Return type:
float
- static ShiftTarget(x0, *args)¶
Error function for disk shift optimization.
- Parameters:
x0 (np.ndarray) – Disk shift values.
*args – a FineOptimize instance and the simulated CBED pattern.
- Returns:
The optimization error.
- Return type:
float
- static callback(intermediate_result, self=None)¶
Callback function for optimization visualization.
- pyextal.optimize.voigt_2d(sigma, gamma, radius)¶
Generates a 2D Voigt profile.
- Parameters:
sigma (float) – Standard deviation for the Gaussian component.
gamma (float) – Half-width at half-maximum for the Lorentzian component.
radius (int) – Half-width of the kernel in pixels; the kernel is (2*radius+1) x (2*radius+1).
- Returns:
A 2D array representing the Voigt profile.
- Return type:
np.ndarray