galfits.mathfunc

Mathematical Functions and Utilities Module

This module provides mathematical utility functions for image analysis, geometric calculations, fitting, and statistical operations used throughout the GalfitS package.

Key Components

  • Geometric functions: Ellipse calculations, coordinate transformations

  • Photometry: Aperture photometry within elliptical apertures

  • Fitting utilities: Polynomial fitting, robust fitting methods

  • Masking: Create masks for various geometric shapes

  • Cross-matching: Match astronomical catalogs

  • Sampling: Grid sampling for parameter space exploration

  • Statistics: Loss functions, total variation regularization

Functions

  • aperture_photometry : Measure flux within elliptical apertures

  • elliptical_func : Distance function for elliptical geometry

  • Maskellipse : Create elliptical mask arrays

  • polynomialfit : Robust polynomial fitting

  • cross_match : Match positions between catalogs

  • loss_total_variation_isotropic : TV regularization for image processing

These functions support both NumPy and JAX arrays for flexibility and GPU acceleration where applicable.

galfits.mathfunc.Maskellipse(mask, posi, a, ellipticity, PA, antimask=False)[source]

Apply elliptical mask to existing mask array.

Adds elliptical region to mask (masking interior) or clears it (antimask=True).

Parameters:
  • mask (array_like, shape (ny, nx)) – Existing mask array (modified in-place conceptually).

  • posi (tuple of float) – Ellipse center (x, y).

  • a (float) – Semi-major axis in pixels.

  • ellipticity (float) – Ellipticity = 1 - b/a.

  • PA (float) – Position angle in degrees from +x axis (counter-clockwise).

  • antimask (bool, default=False) – If False, set interior to 1 (mask it). If True, set interior to 0 (unmask it).

Returns:

Updated mask with same dtype as input.

Return type:

array_like

See also

elliptical_func

Underlying distance function

class galfits.mathfunc.Trial(posi: Tuple[float, float], PA: float)[source]

Bases: object

Parameters:
  • posi (Tuple[float, float])

  • PA (float)

PA: float
posi: Tuple[float, float]
galfits.mathfunc.aperture_photometry(image, posi, a, ellipticity, PA, mask=None, sky_mean=None, sky_std=None)[source]

Measure flux within elliptical aperture with sky subtraction.

Computes aperture photometry in an ellipse with optional sky background estimation from surrounding annulus (1.25a to 1.6a). Returns flux and uncertainty accounting for sky noise and Poisson statistics.

Parameters:
  • image (array_like, shape (ny, nx)) – 2D image array in flux units.

  • posi (tuple of float) – Aperture center (x, y) in pixel coordinates.

  • a (float) – Semi-major axis in pixels.

  • ellipticity (float) – Ellipticity = 1 - b/a, where b is semi-minor axis. Range [0, 1).

  • PA (float) – Position angle in degrees, measured counter-clockwise from +x axis.

  • mask (array_like, shape (ny, nx), optional) – Boolean mask (True = bad pixel to exclude). Default is None.

  • sky_mean (float, optional) – Pre-determined sky background level. If None, estimated from annulus.

  • sky_std (float, optional) – Pre-determined sky noise. If None, estimated from annulus.

Returns:

  • flux (float) – Total sky-subtracted flux within aperture.

  • flux_err (float) – Flux uncertainty from: \(\sqrt{F + (A \\sigma_{\\rm sky})^2 / A_{\\rm annulus} + A \\sigma_{\\rm sky}^2}\)

    Includes source photon noise, sky uncertainty, and sky subtraction error.

Notes

Sky annulus extends from 1.25a to 1.6a. Masked pixels excluded from both aperture and annulus. Useful for measuring galaxy/star fluxes in crowded fields.

Examples

>>> # Measure flux in ellipse at (50, 60) with a=10, e=0.3, PA=45°
>>> flux, err = aperture_photometry(image, (50, 60), 10, 0.3, 45)
>>> print(f"Flux = {flux:.2f} ± {err:.2f}")
galfits.mathfunc.cross_match(catlist, angular_sep=2.5, key0='sc', keyF='scF')[source]

Cross-match multiple astronomical catalogs by sky coordinates.

Recursively joins catalogs using SkyCoord matching. Useful for combining multi-wavelength observations of same sources.

Parameters:
  • catlist (list of Table) – Astropy tables with SkyCoord column (default name ‘sc’).

  • angular_sep (float, default=2.5) – Matching radius in arcseconds.

  • key0 (str, default='sc') – Column name for SkyCoord in input catalogs.

  • keyF (str, default='scF') – Column name for SkyCoord in output merged catalog.

Returns:

Merged catalog with matched sources. Columns from all input catalogs included. Unmatched sources excluded.

Return type:

Table

Notes

For N catalogs, recursively pairs: (1,2), (3,4), …, then pairs results.

Examples

>>> cat1 = Table({'sc': coords1, 'flux_r': [...]})
>>> cat2 = Table({'sc': coords2, 'flux_g': [...]})
>>> matched = cross_match([cat1, cat2], angular_sep=1.0)

See also

make_union_catalog

Find all detections across catalogs

astropy.table.join_skycoord

Underlying matching function

galfits.mathfunc.ellipse_profile(image, posi, a, ellipticity, PA, resolution=200)[source]

measuing the pixel value along the ellipse

Parameters: image: 2D array posi: the center of the ellipse a: the major axis of the ellipse ellipticity: the ellipticity of the ellipse PA: the position angle of the ellipse, degree, since the x axis, anti-clockwise

Return: flux_list, the flux along the ellipse, ordered by the angle

galfits.mathfunc.elliptical_cross_mask(image, posi, a, ellipticity, PA)[source]

Create mask for pixels intersected by ellipse boundary.

Identifies pixels where ellipse boundary crosses, useful for surface brightness profile extraction along ellipse perimeter.

Parameters:
  • image (array_like, shape (ny, nx)) – Input image (used only for shape).

  • posi (tuple of float) – Ellipse center (x, y).

  • a (float) – Semi-major axis in pixels.

  • ellipticity (float) – Ellipticity = 1 - b/a.

  • PA (float) – Position angle in degrees.

Returns:

Binary mask: 1 where ellipse crosses pixel, 0 elsewhere.

Return type:

array_like, shape (ny, nx)

See also

ellipse_profile

Extract flux along ellipse

galfits.mathfunc.elliptical_func(xmesh, posi, a, ellipticity, PA, ymesh=None)[source]

Compute ellipse distance function or solve for y-coordinates.

Returns signed distance from ellipse boundary (negative inside) or solves for y-coordinates on ellipse given x. Used for masking, photometry, and profile extraction.

Parameters:
  • xmesh (array_like) – X-coordinates of pixels or grid.

  • posi (tuple of float) – Ellipse center (x0, y0) in pixels.

  • a (float) – Semi-major axis in pixels.

  • ellipticity (float) – Ellipticity = 1 - b/a, where b is semi-minor axis.

  • PA (float) – Position angle in degrees from +x axis (counter-clockwise).

  • ymesh (array_like, optional) – Y-coordinates. If provided, returns distance function. If None, solves for y given x.

Returns:

If ymesh provided: \(Ax^2 + Bxy + Cy^2 - a^2b^2\)

  • Negative inside ellipse

  • Zero on ellipse

  • Positive outside

If ymesh=None: y-coordinates on ellipse for given x

Return type:

array_like

Notes

Distance formula for rotated ellipse:

\[ \begin{align}\begin{aligned}\begin{split}A = a^2 \\sin^2\\theta + b^2 \\cos^2\\theta\end{split}\\\begin{split}B = 2(b^2 - a^2) \\sin\\theta \\cos\\theta\end{split}\\\begin{split}C = a^2 \\cos^2\\theta + b^2 \\sin^2\\theta\end{split}\end{aligned}\end{align} \]

See also

Maskellipse

Create elliptical mask

aperture_photometry

Flux measurement in ellipse

galfits.mathfunc.elliptical_surface_brightness(image, posi, a_grid, ellipticity, PA)[source]

measuing the mean pixel value along the ellipse sample the a_grid points

Parameters: image: 2D array posi: the center of the ellipse a_grid: the major axis of the ellipse ellipticity: the ellipticity of the ellipse PA: the position angle of the ellipse, degree, since the x axis, anti-clockwise

Return: surface_brightness, the mean flux along the a_grid

galfits.mathfunc.loss_total_variation_isotropic(image)[source]

Compute the isotropic Total Variation (TV) loss of a 2D image.

The isotropic TV is defined as the sum of gradient magnitudes across the image:

\[\mathrm{TV}(I) = \sum_{i,j} \sqrt{\left(\nabla_x I_{i,j}\right)^2 + \left(\nabla_y I_{i,j}\right)^2 + \epsilon}\]

where finite differences are used for the gradients, and a small \(\epsilon\) is added for numerical stability when gradients are zero.

Parameters:

image (array_like, shape (ny, nx)) – Input 2D image.

Returns:

Isotropic TV loss as a scalar value.

Return type:

float

Notes

This implementation uses JAX NumPy if available to support JIT and autodiff.

galfits.mathfunc.make_union_catalog(cataloglist, distance=5)[source]

Cluster sources from multiple catalogs based on their xcentroid and ycentroid coordinates.

Parameters: cataloglist (list): List of source catalogs (each a dictionary or table with ‘xcentroid’ and ‘ycentroid’ keys). distance (float): Maximum distance to consider sources as part of the same cluster.

Returns: list: A (M, N) list where M is the number of unique clusters and N is the number of catalogs. The element of (m,n) indicate the index of source labeled by the m-th cluster at the n-th catalog. And if in the n-th catalog, label m source is not in it (not detected), (m,n)=-1.

galfits.mathfunc.polynomialfit(data, mask, order=3)[source]

Fit and subtract 2D polynomial background from image.

Uses robust least-squares fitting on unmasked regions. Common for sky subtraction in spectroscopy or removing large-scale gradients.

Parameters:
  • data (array_like, shape (ny, nx)) – Input image.

  • mask (array_like, shape (ny, nx)) – Boolean mask (True/1 = exclude from fit).

  • order (int, default=3) – Polynomial degree. order=3 includes terms up to x³, y³, x²y, xy².

Returns:

Dictionary with keys:

  • ’bkgfunc’Polynomial2D model

    Fitted polynomial function

  • ’bkg’array_like

    2D background model

  • ’residual’array_like

    Background-subtracted image (data - bkg)

Return type:

dict

Examples

>>> result = polynomialfit(image, mask, order=2)
>>> clean_image = result['residual']
>>> background = result['bkg']

See also

astropy.modeling.models.Polynomial2D

Underlying model

galfits.mathfunc.sampler(mask, aperture, threshold=0.8, overlap=0.2, sample=0.5, rng=None, max_iterations=50000, max_inner_iterations=2000)[source]

Sample unmasked regions using elliptical apertures.

Parameters:
  • mask (array_like) – Two dimensional mask array where masked pixels should be truthy (1 or True).

  • aperture (dict) – Dictionary describing the aperture with keys posi (center [x, y] in pixels), sma (semi-major axis), ellipticity (0-1) and PA (degrees, anti-clockwise from the y axis to the major axis).

  • threshold (float, optional) – Required fraction of unmasked pixels within an aperture before accepting it.

  • overlap (float, optional) – Maximum allowed fraction of already sampled pixels within the aperture.

  • sample (float, optional) – Fraction of the total unmasked pixels to cover before terminating.

  • rng (numpy.random.Generator or None, optional) – Random generator to use. If None a new default generator is created.

  • max_iterations (int, optional) – Safeguard on the number of outer loop iterations.

  • max_inner_iterations (int, optional) – Safeguard on the number of proposals per accepted aperture.

Returns:

Sequence of accepted apertures represented by their center and position angle (still referenced to the y axis for compatibility with legacy behaviour).

Return type:

list[Trial]