diff dsp/rateconversion/Decimator.cpp @ 0:d7116e3183f8

* Queen Mary C++ DSP library
author cannam
date Wed, 05 Apr 2006 17:35:59 +0000
parents
children f7edcd9138bd
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/dsp/rateconversion/Decimator.cpp	Wed Apr 05 17:35:59 2006 +0000
@@ -0,0 +1,154 @@
+/* -*- c-basic-offset: 4 indent-tabs-mode: nil -*-  vi:set ts=8 sts=4 sw=4: */
+
+/*
+    QM DSP Library
+
+    Centre for Digital Music, Queen Mary, University of London.
+    This file copyright 2005-2006 Christian Landone.
+    All rights reserved.
+*/
+
+#include "Decimator.h"
+
+//////////////////////////////////////////////////////////////////////
+// Construction/Destruction
+//////////////////////////////////////////////////////////////////////
+
+Decimator::Decimator( unsigned int inLength, unsigned int decFactor )
+{
+
+    m_inputLength = 0;
+    m_outputLength = 0;
+    m_decFactor = 1;
+
+    initialise( inLength, decFactor );
+}
+
+Decimator::~Decimator()
+{
+    deInitialise();
+}
+
+void Decimator::initialise( unsigned int inLength, unsigned int decFactor)
+{
+    m_inputLength = inLength;
+    m_decFactor = decFactor;
+    m_outputLength = m_inputLength / m_decFactor;
+
+    decBuffer = new double[ m_inputLength ];
+
+    if( m_decFactor == 4 )
+    {
+	//////////////////////////////////////////////////
+	b[ 0 ] = 0.10133306904918619;
+	b[ 1 ] = -0.2447523353702363;
+	b[ 2 ] = 0.33622528590120965;
+	b[ 3 ] = -0.13936581560633518;
+	b[ 4 ] = -0.13936581560633382;
+	b[ 5 ] = 0.3362252859012087;
+	b[ 6 ] = -0.2447523353702358;
+	b[ 7 ] = 0.10133306904918594;
+
+	a[ 0 ] = 1;
+	a[ 1 ] = -3.9035590278139427;
+	a[ 2 ] = 7.5299379980621133;
+	a[ 3 ] = -8.6890803793177511;
+	a[ 4 ] = 6.4578667096099176;
+	a[ 5 ] = -3.0242979431223631;
+	a[ 6 ] = 0.83043385136748382;
+	a[ 7 ] = -0.094420800837809335;
+	//////////////////////////////////////////////////
+    }
+    else if( m_decFactor == 2 )
+    {
+	//////////////////////////////////////////////////
+	b[ 0 ] = 0.20898944260075727;
+	b[ 1 ] = 0.40011234879814367;
+	b[ 2 ] = 0.819741973072733;
+	b[ 3 ] = 1.0087419911682323;
+	b[ 4 ] = 1.0087419911682325;
+	b[ 5 ] = 0.81974197307273156;
+	b[ 6 ] = 0.40011234879814295;
+	b[ 7 ] = 0.20898944260075661;
+
+	a[ 0 ] = 1;
+	a[ 1 ] = 0.0077331184208358217;
+	a[ 2 ] = 1.9853971155964376;
+	a[ 3 ] = 0.19296739275341004;
+	a[ 4 ] = 1.2330748872852182;
+	a[ 5 ] = 0.18705341389316466;
+	a[ 6 ] = 0.23659265908013868;
+	a[ 7 ] = 0.032352924250533946;
+    }
+    else
+    {
+	//////////////////////////////////////////////////
+	b[ 0 ] = 1;
+	b[ 1 ] = 0;
+	b[ 2 ] = 0;
+	b[ 3 ] = 0;
+	b[ 4 ] = 0;
+	b[ 5 ] = 0;
+	b[ 6 ] = 0;
+	b[ 7 ] = 0;
+
+	a[ 0 ] = 1;
+	a[ 1 ] = 0;
+	a[ 2 ] = 0;
+	a[ 3 ] = 0;
+	a[ 4 ] = 0;
+	a[ 5 ] = 0;
+	a[ 6 ] = 0;
+	a[ 7 ] = 0;
+    }
+
+    resetFilter();
+}
+
+void Decimator::deInitialise()
+{
+    delete [] decBuffer;
+}
+
+void Decimator::resetFilter()
+{
+    Input = Output = 0;
+
+    o1=o2=o3=o4=o5=o6=o7=0;
+}
+
+void Decimator::doAntiAlias(double *src, double *dst, unsigned int length)
+{
+
+    for( unsigned int i = 0; i < length; i++ )
+    {
+	Input = (double)src[ i ];
+
+	Output = Input * b[ 0 ] + o1;
+
+	o1 = Input * b[ 1 ] - Output * a[ 1 ] + o2;
+	o2 = Input * b[ 2 ] - Output * a[ 2 ] + o3;
+	o3 = Input * b[ 3 ] - Output * a[ 3 ] + o4;
+	o4 = Input * b[ 4 ] - Output * a[ 4 ] + o5;
+	o5 = Input * b[ 5 ] - Output * a[ 5 ] + o6;
+	o6 = Input * b[ 6 ] - Output * a[ 6 ] + o7;
+	o7 = Input * b[ 7 ] - Output * a[ 7 ] ;
+
+	dst[ i ] = Output;
+    }
+
+}
+
+void Decimator::process(double *src, double *dst)
+{
+    if( m_decFactor != 1 )
+    {
+	doAntiAlias( src, decBuffer, m_inputLength );
+    }
+    unsigned idx = 0;
+
+    for( unsigned int i = 0; i < m_outputLength; i++ )
+    {
+	dst[ idx++ ] = decBuffer[ m_decFactor * i ];
+    }
+}