Spectra and photometry: overview¶
This area handles the wavelength dimension: spectra and their axes, the Doppler and cosmological shifts that move them, the dust that dims them, and the passbands that turn them into photometry. Everything is a tensor function, so a fit of redshift, dust, and amplitude to a set of magnitudes can run by gradient descent, batched over many objects at once.
The Core Idea: A Spectrum Through the Observation Chain¶
Photometry is the end of a chain of transformations applied to a rest-frame spectral energy distribution (SED). Each link is a separate module with explicit units:
flowchart LR
S["rest-frame SED<br/>F_λ(λ_rest)"] -->|"redshift,<br/>Doppler"| K["observed-frame<br/>spectrum"]
K -->|"dust law<br/>A(λ)"| E["attenuated<br/>spectrum"]
E -->|"passband<br/>integral"| P["flux or<br/>AB magnitude"]
Z["cosmology<br/>D_L(z)"] --> P
The spectrum itself is described by a spectral axis: values plus a type (wavelength, frequency, energy, wavenumber, velocity) and a unit. Rebinning conserves the integrated flux, and invalid or partly covered bins are flagged in a mask rather than renormalized.
Choose a Page¶
| Task | Page | Entry point |
|---|---|---|
| Hold spectra and cubes, convert axes, rebin conserving flux | Spectral axes | SpectralAxis, flux_conserving_rebin |
| Redshift a spectrum, relativistic Doppler shifts, velocity conventions | Kinematics | shift_wavelength, relativistic_doppler_shift |
| Integrate a spectrum through a filter; AB magnitudes | Synthetic photometry | synthetic_photometry, Passband |
| Milky Way or host-galaxy dust attenuation | Extinction | a_lambda, transmission |
| Distances, distance modulus, comoving volume | Cosmology | luminosity_distance, distance_modulus |
| Build a cube from images or IFU frames | Cubes and IFU | coadd_cube |
A Differentiable Magnitude¶
The spectrum below is the SDSS quasar 0751-52251-0160 (z = 0.0456), averaged in 50 Å bins across the r band; the bump at 6870 Å is its redshifted Hα line. The passband is the SDSS r total throughput from the SVO Filter Profile Service, sampled every 50 Å. The synthetic AB magnitude agrees with the one the SDSS pipeline computed from the full-resolution spectrum (16.764) to 0.012 mag. Correcting for Milky Way dust with \(E(B-V) = 0.0698\) (Schlafly and Finkbeiner 2011 at this position) brightens it by 0.18 mag, and the gradient of the magnitude with respect to \(E(B-V)\) is the extinction coefficient of the band.
import torch
from torchsky.extinction import a_lambda
from torchsky.spectrophotometry import Passband, synthetic_photometry
f64 = dict(dtype=torch.float64)
wave = torch.arange(5325.0, 7350.0, 50.0, **f64) # bin centres, Angstrom
flux = 1e-17 * torch.tensor([ # erg/s/cm2/A
52.11, 52.35, 50.37, 54.77, 54.70, 55.99, 55.68, 54.61, 53.47, 54.81, 54.05, 53.31,
53.13, 54.38, 55.37, 56.69, 56.59, 54.48, 55.89, 55.18, 56.72, 55.88, 54.85, 53.92,
52.73, 55.15, 55.09, 56.96, 58.42, 67.85, 78.72, 84.65, 70.60, 59.98, 58.63, 53.83,
54.05, 53.48, 54.12, 54.38, 54.44,
], **f64)
sdss_r = Passband(
torch.arange(5350.0, 7301.0, 50.0, **f64),
torch.tensor([
0.0000, 0.0011, 0.0227, 0.0745, 0.1537, 0.2463, 0.3256, 0.3789, 0.4120, 0.4317,
0.4436, 0.4519, 0.4592, 0.4659, 0.4700, 0.4716, 0.4741, 0.4787, 0.4839, 0.4883,
0.4908, 0.4912, 0.4914, 0.4913, 0.4883, 0.4825, 0.4476, 0.3601, 0.2439, 0.1265,
0.0441, 0.0150, 0.0081, 0.0042, 0.0021, 0.0013, 0.0008, 0.0002, 0.0000, 0.0000,
], **f64),
name="SDSS r",
)
observed = synthetic_photometry(wave, flux, sdss_r, output="ab_mag")
assert bool(observed.valid) and abs(observed.value.item() - 16.764) < 0.02
ebv = torch.tensor(0.0698, **f64, requires_grad=True)
dereddened = flux * 10.0 ** (0.4 * a_lambda(wave, ebv=ebv, law="f99"))
corrected = synthetic_photometry(wave, dereddened, sdss_r, output="ab_mag")
corrected.value.backward()
r_band = a_lambda(sdss_r.pivot_wavelength.reshape(1), ebv=1.0, law="f99") # A_r / E(B-V)
assert abs((observed.value - corrected.value).item() - 0.18) < 0.01
assert abs(-ebv.grad.item() / r_band.item() - 1.0) < 0.01
The SDSS spectrum example reads the full spectrum, moves it to the rest frame with the pipeline redshift, checks the [O III] line centroids, and computes all five ugriz magnitudes.
Conventions and Pitfalls¶
- Wavelengths are Angstrom unless a
wavelength_unitargument says otherwise; conversion happens once at the boundary. - Flux densities are \(F_\lambda\) for photometry. AB magnitudes and microjansky outputs need cgs \(F_\lambda\) (erg s⁻¹ cm⁻² Å⁻¹).
- Velocities are signed. Positive radial velocity is receding, in metres
per second for
relativistic_doppler_shift. - Coverage is reported, not corrected. A passband that extends beyond the
spectrum gives
valid=Falseand NaN belowmin_coverage; nothing is renormalized silently. - Masks mean "this sample exists" (
Trueis good) in spectra and photometry. Map products use data-quality bits instead; check each function. - Precision. Passband samples are held in float64 on CPU and CUDA. MPS keeps the tensor's own float32 dtype, with correspondingly lower precision.
Signatures are in the torchsky.spectral,
torchsky.spectrophotometry,
torchsky.extinction,
torchsky.redshift, and
torchsky.cosmology references.
Tabulated filter profiles (torchsky.filter_profiles) are experimental.
Connections¶
Spectral FITS axes are decoded by the WCS. Cubes and IFU build spatial-spectral products from images, and the experimental field models render through the same passband integrals. Photometric redshift encoders for machine learning are described with the encoders.
Examples on real data: the SDSS quasar spectrum and the MaNGA IFU cube.