Mercurial > hg > aim92
view tools/freqs.c @ 0:5242703e91d3 tip
Initial checkin for AIM92 aimR8.2 (last updated May 1997).
author | tomwalters |
---|---|
date | Fri, 20 May 2011 15:19:45 +0100 |
parents | |
children |
line wrap: on
line source
/************************************************************************** Filter-bank routines. ====================== Filter-bank parameters in model headers are as follows: (These may be converted, using the given routines, into values which are then passed as args into the routines below. All the values are double except for the number of channels which is an int. Remember to cast Freq as double). String name Conversion Value Comment ------------- ----------- --------- ------------------------------------- channels_afb Optionint() channels Number of channels in filter mincf_afb Freq() mincf Minimum center frequency (Hz) maxcf_afb Freq() maxcf Maximum center frequency (Hz) dencf_afb atof() dencf Filter density (filters/critical band) bwmin_afb Freq() bwmin Minimum filter bandwith quality_afb Freq() quality Ultimate qualtity factor of filters Initialize global filter parameters. SetErbParameters( bwmin, quality ) double bwmin, quality ; Return array of centre frequencies for given density. double *GenerateCenterFrequencies( mincf, maxcf, dencf ) double mincf, maxcf, dencf ; (This uses routine GenerateScale() to compute the scale, and uses routine ErbScale() to convert the parameters (mincf etc) into Erbs). Return array of centre frequencies for given number of channels. double *NumberedCenterFrequencies( mincf, maxcf, channels ) double mincf, maxcf ; int channels ; (This uses routine NumberedScale() to compute the scale, and uses routine ErbScale() to convert the parameters (mincf etc) into Erbs). Return number of channels for given density. int NumberCenterFrequencies( mincf, maxcf, dencf ) double mincf, maxcf, dencf ; Basic utilities: ErbScale() Convert freq in Hz to Erbs. Example of application ---------------------- #include "freqs.c" int channels = 0 ; double mincf = 220. ; double maxcf = 4400. ; double dencf = 4. ; double bwmin = 24.7 ; double quality = 9.265 ; SetErbParameters( bwmin, quality ) ; if (channels==0) { frequencies = GenerateCenterFrequencies( mincf, maxcf, dencf ) ; channels = NumberCenterFrequencies( mincf, maxcf, dencf ) ; } else frequencies = NumberedCenterFrequencies( mincf, maxcf, channels ) ; **************************************************************************/ extern void SetErbParameters() ; extern double Erb(), ErbScale(), FofErbScale() ; extern double *GenerateCenterFrequencies() ; extern int NumberCenterFrequencies() ; extern double *NumberedCenterFrequencies() ; extern double *GenerateScale() ; extern int NumberOnScale() ; extern double *NumberedScale() ; /* Defaults */ static double limit = 24.7 ; static double Q = 9.265 ; /********************** filter/gamma_tone.c *******************************/ double bankBaseFrequency = 1000. ; double *GenerateCenterFrequencies( min_cf, max_cf, erb_density ) double min_cf, max_cf, erb_density ; { return ( GenerateScale( ErbScale( min_cf ), ErbScale( max_cf ), erb_density, ErbScale( bankBaseFrequency ), FofErbScale ) ) ; } int NumberCenterFrequencies( min_cf, max_cf, erb_density ) double min_cf, max_cf, erb_density ; { return ( NumberOnScale( ErbScale( min_cf ), ErbScale( max_cf ), erb_density, ErbScale( bankBaseFrequency ) ) ) ; } double *NumberedCenterFrequencies( min_cf, max_cf, channels ) double min_cf, max_cf ; int channels ; { return ( NumberedScale( ErbScale( min_cf ), ErbScale( max_cf ), channels, FofErbScale ) ) ; } /********************** filter/scales.c ************************************/ double *GenerateScale( min, max, density, base, inverse ) double min, max, density, base, (*inverse)() ; { unsigned n_scale = NumberOnScale( min, max, density, base ) ; double *scale ; double scale_start ; int i ; scale = (double *)malloc( (n_scale+1) * sizeof(double) ) ; if( min != max ) { scale_start = base - floor( ( base - min ) * density ) / density ; /* fill array scale points 1./density apart */ for( i=0 ; i < n_scale ; i++ ) scale[ i ] = scale_start + i / density ; scale[ i++ ] = 0. ; } else { scale[0] = min ; scale[1] = 0. ; } /* convert scale space back to units required */ if( inverse != (double ( * )()) 0 ) for( i=0 ; i < n_scale ; i++ ) scale[ i ] = inverse( scale[ i ] ) ; return ( scale ) ; } int NumberOnScale( min, max, density, base ) double min, max, density, base ; { if( min != max ) return ( ( int ) ( ( floor( ( base - min ) * density ) + 1. + ( floor( ( max - base ) * density ) ) ) ) ) ; else return ( 1 ) ; } double *NumberedScale( min, max, channels, inverse ) double min, max ; int channels ; double (*inverse)() ; { double *scale ; int chan ; scale = (double *)malloc( (channels+1) * sizeof(double) ) ; scale[ 0 ] = min ; for( chan=1 ; chan < channels ; chan++ ) scale[ chan ] = min + chan * (max-min) / ( channels - 1 ) ; if( inverse != (double ( * )()) 0 ) for( chan=0 ; chan < channels ; chan++ ) scale[ chan ] = inverse( scale[ chan ] ) ; scale[ channels ] = 0. ; return ( scale ) ; } /********************** filter/formulae.c ************************************/ void SetErbParameters( new_limit, new_Q ) double new_limit, new_Q ; { limit = new_limit ; Q = new_Q ; return ; } double ErbScale( frequency ) double frequency ; { return ( log( 1. + frequency / Q / limit ) * Q ) ; } double FofErbScale( E ) double E ; { return ( ( exp( E / Q ) - 1 ) * Q * limit ) ; }