VQT
Variable-Q transform: the general form of the CQT with a
bandwidth offset gamma that widens the low-frequency filters
[schorkhuber2010], shortening their wavelets
and improving time resolution where the constant-Q filters grow long.
specux.cqt is exactly specux.vqt at gamma=0.
specux.vqt(x, *, sr, hop_length=512, fmin=None, n_bins=84, bins_per_octave=12, gamma=None, filter_scale=1.0, sparsity=0.01, tuning=0.0, output="magnitude", eps=1e-10, backend="auto")import numpy as np
import specux
x = np.random.randn(8, 4 * 22050).astype(np.float32)V = specux.vqt(x, sr=22050, n_bins=84) # gamma=None: ERB defaultV.shape # (8, 84, 173) = (..., n_bins, n_frames)import torch
import specux
xt = torch.randn(8, 4 * 22050, device="cuda", requires_grad=True)V = specux.vqt(xt, sr=22050, n_bins=84, gamma=10.0)V.sum().backward()import cupy
import specux
xc = cupy.random.standard_normal((8, 4 * 22050), dtype=cupy.float32)V = specux.vqt(xc, sr=22050, n_bins=84)The gamma parameter
Each filter’s bandwidth is alpha * f + gamma: a constant-Q term plus a
fixed offset in Hz.
gamma=None(default): the offset follows the ERB model of human auditory filters [glasberg1990], so low-frequency bins get bandwidths closer to perception.gamma=0: the constant-Q limit; identical tospecux.cqtbit for bit.gamma>0: a fixed offset in Hz.
Everything else (parameters, shapes, gradients, backends, and the
specux.transforms.VQT Module) matches the CQT page.
The configured form
t = specux.VQT(sr=22050, n_bins=84, gamma=10.0)V = t(x) # (..., n_bins, n_frames)assert specux.VQT(**t.to_dict()) == tReferences
- [schorkhuber2010]: the variable-Q formulation.
- [glasberg1990]: the ERB bandwidth model.