# HG changeset patch # User Chris Cannam # Date 1399629383 -3600 # Node ID 51f5f0deef2fdfcf4abd8da575cedd5d97ded305 # Parent bfc7cf71f2ef05c0f1454b32acefdd4545c58366 Bit more on inverse diff -r bfc7cf71f2ef -r 51f5f0deef2f cpp-qm-dsp/CQInverse.cpp --- a/cpp-qm-dsp/CQInverse.cpp Fri May 09 10:05:16 2014 +0100 +++ b/cpp-qm-dsp/CQInverse.cpp Fri May 09 10:56:23 2014 +0100 @@ -31,24 +31,18 @@ #include "CQInverse.h" -#include "CQKernel.h" - #include "dsp/rateconversion/Resampler.h" #include "maths/MathUtilities.h" #include "dsp/transforms/FFT.h" #include -#include #include #include using std::vector; -using std::complex; using std::cerr; using std::endl; -typedef std::complex C; - CQInverse::CQInverse(double sampleRate, double minFreq, double maxFreq, @@ -145,13 +139,23 @@ m_fft = new FFTReal(m_p.fftSize); } -std::vector process(const std::vector > &blocks) +CQInverse::RealSequence +CQInverse::process(const ComplexBlock &block) { // The input data is of the form produced by ConstantQ::process -- // an unknown number N of columns of varying height. We assert - // that N is a multiple of atomsPerFrame * 2^(octaves-1). - // - // Our procedure: + // that N is a multiple of atomsPerFrame * 2^(octaves-1), as must + // be the case for data that came directly from our ConstantQ + // implementation. + + int blockWidth = m_p.atomsPerFrame * int(pow(2, m_octaves - 1)); + if (block.size() % blockWidth != 0) { + throw std::invalid_argument + ("Input block size must be a multiple of processing block width " + "(atoms-per-frame * 2^(octaves-1))"); + } + + // Procedure: // // 1. Slice the list of columns into a set of lists of columns, // one per octave, each of width N / (2^octave-1) and height @@ -168,7 +172,7 @@ // 4. Overlap-add each octave's resynthesised blocks (unwindowed) // // 5. Resample each octave's overlap-add stream to the original - // rate, and sum + // rate, and sum. } diff -r bfc7cf71f2ef -r 51f5f0deef2f cpp-qm-dsp/CQInverse.h --- a/cpp-qm-dsp/CQInverse.h Fri May 09 10:05:16 2014 +0100 +++ b/cpp-qm-dsp/CQInverse.h Fri May 09 10:56:23 2014 +0100 @@ -29,17 +29,16 @@ authorization. */ -#ifndef CQ_INVERSE_H -#define CQ_INVERSE_H +#ifndef CQINVERSE_H +#define CQINVERSE_H +#include "CQBase.h" #include "CQKernel.h" -#include - class Resampler; class FFTReal; -class CQInverse +class CQInverse : public CQBase { public: CQInverse(double sampleRate, @@ -47,24 +46,22 @@ int binsPerOctave); ~CQInverse(); - double getSampleRate() const { return m_sampleRate; } - int getBinsPerOctave() const { return m_binsPerOctave; } - int getOctaves() const { return m_octaves; } - int getTotalBins() const { return m_octaves * m_binsPerOctave; } - int getColumnHop() const { return m_p.fftHop / m_p.atomsPerFrame; } - int getLatency() const { return m_outputLatency; } - double getMaxFrequency() const { return m_p.maxFrequency; } - double getMinFrequency() const; // actual min, not that passed to ctor - double getBinFrequency(int bin) const; + virtual double getSampleRate() const { return m_sampleRate; } + virtual int getBinsPerOctave() const { return m_binsPerOctave; } + virtual int getOctaves() const { return m_octaves; } + virtual int getTotalBins() const { return m_octaves * m_binsPerOctave; } + virtual int getColumnHop() const { return m_p.fftHop / m_p.atomsPerFrame; } + virtual int getLatency() const { return m_outputLatency; } + virtual double getMaxFrequency() const { return m_p.maxFrequency; } + virtual double getMinFrequency() const; // actual min, not that passed to ctor + virtual double getBinFrequency(int bin) const; - // Input is the format produced by ConstantQ class, not - // CQInterpolated (or can we make this support either?) + // Input is the format produced by ConstantQ class, + // i.e. uninterpolated complex, not the real-valued stuff produced + // by CQSpectrogram - //!!! no, we need complex not magnitudes! CQ should probably - //!!! produce totally raw output and something like CQInterpolated - //!!! do the magnitude stuff as well as interpolation - std::vector process(const std::vector > &); - std::vector getRemainingOutput(); + RealSequence process(const ComplexBlock &); + RealSequence getRemainingOutput(); private: double m_sampleRate; diff -r bfc7cf71f2ef -r 51f5f0deef2f cpp-qm-dsp/ConstantQ.cpp --- a/cpp-qm-dsp/ConstantQ.cpp Fri May 09 10:05:16 2014 +0100 +++ b/cpp-qm-dsp/ConstantQ.cpp Fri May 09 10:56:23 2014 +0100 @@ -38,12 +38,10 @@ #include "dsp/transforms/FFT.h" #include -#include #include #include using std::vector; -using std::complex; using std::cerr; using std::endl; diff -r bfc7cf71f2ef -r 51f5f0deef2f cpp-qm-dsp/Makefile --- a/cpp-qm-dsp/Makefile Fri May 09 10:05:16 2014 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,38 +0,0 @@ - -DEFINES := -DUSE_PTHREADS - -CFLAGS := -I../.. $(CFLAGS) $(DEFINES) - -#CXXFLAGS := -I../.. -fPIC -Wall -g $(CXXFLAGS) $(DEFINES) -CXXFLAGS := -I../.. -fPIC -Wall -O3 -ffast-math -ftree-vectorize $(CXXFLAGS) $(DEFINES) - -LDFLAGS := $(LDFLAGS) - -#VG := valgrind - -LIBS := ../../qm-dsp/libqm-dsp.a -lpthread -PROGRAM_LIBS := -lsndfile - -SOURCES := CQKernel.cpp ConstantQ.cpp test.cpp - -OBJECTS := $(SOURCES:.cpp=.o) -OBJECTS := $(OBJECTS:.c=.o) - -PROGRAM := test - -all: $(PROGRAM) - -test: $(OBJECTS) - $(CXX) -o $@ $^ $(LDFLAGS) $(LIBS) $(PROGRAM_LIBS) - -clean: - rm -f *.o - -depend: - makedepend -Y $(SOURCES) - -# DO NOT DELETE - -CQKernel.o: CQKernel.h -ConstantQ.o: ConstantQ.h CQKernel.h -test.o: ConstantQ.h CQKernel.h