braintools.analysis.spectral.morlet_transform#
- braintools.analysis.spectral.morlet_transform(x, dt, freqs, n_cycles=7.0, *, zero_mean=True)#
Compute the complex Morlet wavelet transform along time axis 0.
For each frequency \(f\) with \(\sigma_t = n_{cycles} / (2\pi f)\), the wavelet [1]
\[W_f(t) = c \, \left(e^{2\pi i f t} - \kappa\right) e^{-t^2 / (2\sigma_t^2)}, \qquad |t| < 5\sigma_t,\]is sampled at
dt(with a sample at exactlyt = 0), where \(\kappa = e^{-2(\pi f \sigma_t)^2}\) ifzero_meanelse 0, and \(c\) makes \(\|W_f\|_2 = \sqrt{2}\) (MNE’s normalisation). The signal is convolved with each wavelet ('same'mode, the output aligned with the input samples, zero padding outside the signal) via the FFT.- Parameters:
x (
Array|ndarray|bool|number|bool|int|float|complex|Quantity) – Real signal of shape(T, ...); time is axis 0. Abrainunit.Quantityis accepted.dt (
float|Quantity) – Sampling interval (seconds if a plain number). Static.freqs (
Sequence[float]) – Wavelet frequencies in Hz,0 < f <= fs / 2. Static.n_cycles (
float|Sequence[float]) – Number of cycles of each wavelet (one value, or one per frequency). Static.zero_mean (
bool) – Subtract the Gaussian-weighted offset so each wavelet has zero mean (the default ofmne.time_frequency.tfr_array_morlet).
- Returns:
tfr – Complex coefficients of shape
(n_freqs, T, ...);abs(tfr)**2is the power andangle(tfr)the phase. Carries the unit ofx.- Return type:
Array|Quantity- Raises:
ValueError – If a frequency is not in
(0, fs / 2],n_cycleshas the wrong length or is not positive, or the longest wavelet is longer thanT(as in MNE).
See also
spectrogramShort-time Fourier power spectrogram.
analytic_signalHilbert-transform analytic signal.
Notes
The result equals
mne.time_frequency.tfr_array_morlet(x.T[None], sfreq=fs, freqs=freqs, n_cycles=n_cycles, zero_mean=zero_mean, output='complex')[0]with the channel axis moved behind the time axis. The wavelets are designed on the host and their FFTs (lengthnext_fast_len(T + L_max - 1), which avoids circular wrap-around) are constants; the convolution runs in JAX.The function is jittable and vmappable and differentiable with respect to
x.References
Examples
>>> import jax.numpy as jnp >>> from braintools.analysis.spectral import morlet_transform >>> t = jnp.arange(2000) * 1e-3 >>> x = jnp.sin(2 * jnp.pi * 20 * t) >>> tfr = morlet_transform(x, dt=1e-3, freqs=[10.0, 20.0, 40.0]) >>> tfr.shape (3, 2000) >>> power = jnp.mean(jnp.abs(tfr[:, 500:1500]) ** 2, axis=1) >>> int(jnp.argmax(power)) 1