Harmonic spectrum#
Per-frequency harmonicity H(f) on a single signal. This is the H-only entry point of biotuner’s spectral resonance machinery.
Quick start#
from biotuner.harmonic_spectrum import compute_harmonic_spectrum
freqs, H, S, summary = compute_harmonic_spectrum(
signal, precision_hz=0.5, fmin=2, fmax=30, fs=1000,
)
# H — per-frequency harmonicity spectrum (n_freqs,)
# S — N×N kernel similarity matrix
# summary — dict of complexity metrics (flatness, entropy, higuchi, ...)
Sister modules#
For the full H × PC = R pipeline (with surrogate normalization, swappable
kernels, and higher-order coupling extensions), use
biotuner.resonance.compute_resonance().
For cross-channel analyses (two-or-more signals), use
biotuner.harmonic_connectivity.
Public API#
compute_harmonic_spectrum()— main entry pointharmonicity_matrices()— N×N similarity matrix (legacy helper)compute_harmonic_power()— probability-weighted reduction of S to H(f)find_spectral_peaks()— peak detector (shared across the resonance package)harmonic_entropy()— complexity DataFrame for H / PC / R togetherget_harmonic_ratio()— best (n, m) within tolerance for a freq paircount_theoretical_harmonic_partners()— bandwidth-correction helper
biotuner.harmonic_spectrum — harmonicity-field computations from PSDs.
Module type: Functions
This module is the H-only entry point of biotuner’s spectral resonance machinery. For per-frequency harmonicity H(f) on a single signal, this is the right module.
Quick start#
from biotuner.harmonic_spectrum import compute_harmonic_spectrum
freqs, H, S, summary = compute_harmonic_spectrum(
signal, precision_hz=0.5, fmin=2, fmax=30, fs=1000,
)
# H — per-frequency harmonicity spectrum (n_freqs,)
# S — N×N kernel similarity matrix
# summary — dict of complexity metrics (flatness, entropy, higuchi, ...)
Sister modules#
biotuner.resonance— full H × PC = R pipeline with surrogate normalization, swappable kernels, and higher-order coupling extensions. Usecompute_resonance(signal, sf, config=...)when you want the full per-frequency resonance spectrum, not just H(f).biotuner.harmonic_connectivity— cross-channel analogs. Usecompute_cross_resonance(sig1, sig2, sf)for two signals,harmonic_connectivity(...).compute_cross_resonance_connectivity(...)for N-channel matrices.
Public API#
compute_harmonic_spectrum()— main entry pointharmonicity_matrices()— N×N similarity matrix (legacy helper)compute_harmonic_power()— probability-weighted reduction of S to H(f)find_spectral_peaks()— peak detector (shared across the resonance package)harmonic_entropy()— complexity DataFrame for H / PC / R togetherget_harmonic_ratio()— best (n, m) within tolerance for a freq paircount_theoretical_harmonic_partners()— bandwidth-correction helper
- compute_harmonic_spectrum(signal, precision_hz, *, fmin=1, fmax=30, fs=1000, noverlap=1, smoothness=1, smoothness_harm=1, power_law_remove=True, harmonic_kernel='harmsim', harmonic_kernel_params=None, n_peaks=5, normalize=True, bandwidth_correction=False, psd_normalization='minmax_prob', legacy_self_pair_subtract=True)[source]#
Compute the harmonicity spectrum H(f) and its complexity summary.
This is the narrow, H-only entry point — replaces the harmonicity portion of the legacy
compute_global_harmonicity. For the full H/PC/R triple usebiotuner.resonance.compute_resonance().Under the hood this dispatches the harmonic kernel from the
biotuner.resonanceregistry, so all kernels added in later phases (sethares, stolzenburg, harmonic_entropy, hopf, lorentzian) become available automatically by name.- Parameters:
signal (1-D array)
precision_hz (float)
fmin, fmax (float)
fs (int, sampling frequency)
noverlap (int, STFT overlap)
smoothness (float, divides STFT nperseg)
smoothness_harm (float, Gaussian smoothing on H before summary)
power_law_remove (bool, FOOOF aperiodic removal)
harmonic_kernel (str, name in
biotuner.resonance.registry.HARMONIC_KERNELS) –'harmsim'(default) |'subharm_tension'(legacy) | future kernels.harmonic_kernel_params (dict, passed to the kernel)
n_peaks (int, peaks returned by the summary)
normalize (bool, legacy normalize flag for the per-bin reducer)
bandwidth_correction (bool, legacy bandwidth correction)
psd_normalization (‘minmax_prob’ (legacy) | ‘prob’ | ‘none’)
legacy_self_pair_subtract (bool, reproduce legacy self-pair-subtract reducer)
- Returns:
freqs (ndarray (n_freqs,))
H_values (ndarray (n_freqs,) – the harmonicity spectrum)
harmonicity_matrix (ndarray (n_freqs, n_freqs) – the kernel similarity matrix)
summary (dict) – spectrum_complexity output: flatness, entropy, spread, higuchi, peaks, peak_indices, avg, max, peaks_avg, peak_harmsim, peak_harmsim_avg, peak_harmsim_max.
Examples
>>> freqs, H, M, summary = compute_harmonic_spectrum(signal, 0.5, fmin=2, fmax=30) >>> summary['flatness'], summary['entropy'], summary['peaks']
- harmonicity_matrices(freqs, metric='harmsim', n_harms=5, delta_lim=150, min_notes=2)[source]#
Compute harmonicity matrix of frequencies.
- Parameters:
freqs (ndarray) – Array of frequencies.
metric (str, optional) – The metric to compute dyad similarity. Default is ‘harmsim’.
n_harms (int, optional) – The number of harmonics. Default is 5.
delta_lim (int, optional) – The delta limit. Default is 150.
min_notes (int, optional) – The minimum number of notes. Default is 2.
- Returns:
ndarray – The harmonicity matrix.
See also
biotuner.resonance.kernels_harmonic.kernel_harmsimnew strategy-registry version with the same numerics, plus support for additional kernels (sethares, stolzenburg, harmonic_entropy, hopf, lorentzian) in later phases.
- compute_harmonic_power(freqs, dyad_similarities, psd_clean, normalize=True, bandwidth_correction=False, fmin=1, fmax=30)[source]#
Compute harmonicity as probability-weighted average of dyad similarities.
The harmonicity of frequency i represents the expected harmonic similarity with other frequencies, weighted by the joint probability of observing each frequency pair. This formulation is scale-invariant and not sensitive to spectral shape or total power distribution.
- Parameters:
freqs (ndarray) – Array of frequencies.
dyad_similarities (ndarray) – Dyad similarities matrix.
psd_clean (ndarray) – The cleaned Power Spectral Density (PSD).
normalize (bool, default=True) – If True, compute harmonicity as weighted average (recommended). If False, compute as sum of weighted harmonic contributions.
bandwidth_correction (bool, default=False) – If True, apply correction for bandwidth bias where lower frequencies have more potential harmonic partners within the analysis range.
fmin (float, default=1) – Minimum frequency of analysis bandwidth (used for bandwidth correction).
fmax (float, default=30) – Maximum frequency of analysis bandwidth (used for bandwidth correction).
- Returns:
tuple of ndarrays – The harmonicity values and the harmonicity matrix.
See also
biotuner.resonance.coupling.reduce_matrix_to_spectrumstrategy-registry version supporting both the legacy self-pair-subtract reduction and the clean off-diagonal-mask reduction recommended for new code.
Notes
The weighting uses psd_prob[i] * psd_prob[j] which requires both frequencies to have high power for high harmonicity contribution.
- find_spectral_peaks(values, freqs, n_peaks, prominence_threshold=0.5)[source]#
Identify the prominent spectral peaks in a frequency spectrum.
This function uses the peak prominence to select the most notable peaks, and returns their frequencies and indices. Prominence is a measure of how much a peak stands out due to its intrinsic height and its location relative to other peaks.
- Parameters:
values (array_like) – 1-D array of values for the frequency spectrum.
freqs (array_like) – 1-D array of frequencies corresponding to the values in ‘values’.
n_peaks (int) – The number of top prominent peaks to return.
prominence_threshold (float, default=0.5) – The minimum prominence a peak must have to be considered notable.
- Returns:
peak_frequencies (ndarray) – Frequencies of the ‘n_peaks’ most prominent peaks.
prominent_peaks (ndarray) – Indices in ‘values’ and ‘freqs’ of the ‘n_peaks’ most prominent peaks.
See also
scipy.signal.find_peaks,scipy.signal.peak_prominencesExamples
>>> values = np.array([0, 1, 0, 2, 0, 3, 0, 2, 0, 1, 0]) >>> freqs = np.array([10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 110]) >>> find_spectral_peaks(values, freqs, n_peaks=3) (array([60, 40, 80]), array([5, 3, 7]))
- harmonic_entropy(freqs, harmonicity_values, phase_coupling_values, resonance_values)[source]#
Compute spectral features and Higuchi Fractal Dimension of Harmonicity, Phase Coupling, and Resonance spectra.
This function calculates several spectral properties: flatness, entropy, spread, and Higuchi Fractal Dimension for three input spectra: Harmonicity, Phase Coupling, and Resonance. Results are returned as a pandas DataFrame.
- Parameters:
freqs (array_like) – 1-D array of frequencies common for all the spectra.
harmonicity_values (array_like) – 1-D array of spectral values for the Harmonicity spectrum.
phase_coupling_values (array_like) – 1-D array of spectral values for the Phase Coupling spectrum.
resonance_values (array_like) – 1-D array of spectral values for the Resonance spectrum.
- Returns:
harmonic_complexity (DataFrame) – A pandas DataFrame with spectral flatness, entropy, spread, and Higuchi Fractal Dimension for each of the Harmonicity, Phase Coupling, and Resonance spectra.
See also
biotuner.metrics.spectrum_complexitysingle-spectrum version returning a dict; used by both this function and the resonance orchestrator.
- get_harmonic_ratio(freq_i, freq_j, max_n=3, max_m=3, tolerance=0.05)[source]#
Identify if two frequencies are at an n:m harmonic ratio.
- Parameters:
freq_i (float) – First frequency.
freq_j (float) – Second frequency.
max_n (int, default=3) – Maximum value for n in n:m ratio.
max_m (int, default=3) – Maximum value for m in n:m ratio.
tolerance (float, default=0.05) – Relative tolerance for ratio matching (5%).
- Returns:
tuple or None – (n, m) if frequencies are harmonically related, None otherwise.
See also
biotuner.resonance.kernels_ratio.binary_nm_kernelvectorized version operating on freq arrays (returns W, N, M matrices).
- count_theoretical_harmonic_partners(freq, fmin, fmax, max_ratio=5)[source]#
Count theoretical maximum number of harmonic partners within bandwidth.
This function counts how many frequencies at simple n:m ratios (up to max_ratio) would fall within the analysis bandwidth [fmin, fmax] for a given frequency. Lower frequencies have more potential partners, creating systematic bias.
- Parameters:
freq (float) – The frequency to analyze.
fmin (float) – Minimum frequency of analysis bandwidth.
fmax (float) – Maximum frequency of analysis bandwidth.
max_ratio (int, default=5) – Maximum value for n and m in n:m ratios to consider.
- Returns:
int – Number of theoretical harmonic partners within bandwidth.