gpt4 book ai didi

iphone - 核心音频,Goertzel 算法不起作用

转载 作者:太空狗 更新时间:2023-10-30 03:51:33 26 4
gpt4 key购买 nike

我目前正在创建一个应用程序,它可以通过 iPhone 的麦克风实时计算预定义频率 (16780Hz) 的幅度。

我的缓冲区中有声音数据,我尝试使用专为该任务设计的算法 Goertzel 来处理它。 Goertzel info .这就是问题开始的地方。

当录制的声音频率 (5000Hz) 远低于定义频率 (16780Hz) 时,该算法会给出非常积极的结果。事实上,与录制正确频率的声音时产生的结果相比,结果要积极得多。

这是我对 goertzel 的实现:

double goertzel(unsigned short *sample, int sampleRate, double Freq, int len )
{

double realW = 2.0 * cos(2.0 * M_PI * Freq / sampleRate);
double imagW = 2.0 * sin(2.0 * M_PI * Freq / sampleRate);
double d1 = 0;
double d2 = 0;
int z;
double y;
for (int i = 0; i < len; i++) {
y=(double)(signed short)sample[i] +realW * d1 - d2;
d2 = d1;
d1 = y;
}
double rR = 0.5 * realW *d1-d2;
double rI = 0.5 * imagW *d1-d2;

return (sqrt(pow(rR, 2)+pow(rI,2)))/len;
} /* end function goertzel */

以下是我如何检索音频(如果它完全相关)

-(void)startListeningWithFrequency:(float)frequency;
{
OSStatus status;
//AudioComponentInstance audioUnit;
AudioComponentDescription desc;
desc.componentType = kAudioUnitType_Output;
desc.componentSubType = kAudioUnitSubType_RemoteIO;
desc.componentFlags = 0;
desc.componentFlagsMask = 0;
desc.componentManufacturer = kAudioUnitManufacturer_Apple;

AudioComponent inputComponent = AudioComponentFindNext(NULL, &desc);
status = AudioComponentInstanceNew( inputComponent, &audioUnit);
checkStatus(status);

UInt32 flag = 1;
status = AudioUnitSetProperty(audioUnit, kAudioOutputUnitProperty_EnableIO, kAudioUnitScope_Input,kInputBus, &flag, sizeof(flag));
checkStatus(status);

AudioStreamBasicDescription audioFormat;
audioFormat.mSampleRate = 44100.00;//44100.00;
audioFormat.mFormatID = kAudioFormatLinearPCM;
audioFormat.mFormatFlags = kAudioFormatFlagIsPacked | kAudioFormatFlagIsSignedInteger;
audioFormat.mFramesPerPacket = 1;
audioFormat.mChannelsPerFrame = 1;
audioFormat.mBitsPerChannel = 16;
// float
audioFormat.mBytesPerPacket = 2;
audioFormat.mBytesPerFrame = 2;

status = AudioUnitSetProperty(audioUnit,
kAudioUnitProperty_StreamFormat,
kAudioUnitScope_Output,
kInputBus,
&audioFormat,
sizeof(audioFormat));
checkStatus(status);
//status = AudioUnitSetProperty(audioUnit,
// kAudioUnitProperty_StreamFormat,
// kAudioUnitScope_Input,
// kOutputBus,
// &audioFormat,
// sizeof(audioFormat));
checkStatus(status);
AURenderCallbackStruct callbackStruct;
callbackStruct.inputProc = recordingCallback;
callbackStruct.inputProcRefCon = self;
status = AudioUnitSetProperty(audioUnit,
kAudioOutputUnitProperty_SetInputCallback,
kAudioUnitScope_Global,
kInputBus, &callbackStruct, sizeof(callbackStruct));
checkStatus(status);
/* UInt32 shouldAllocateBuffer = 1;
AudioUnitSetProperty(audioUnit, kAudioUnitProperty_ShouldAllocateBuffer, kAudioUnitScope_Global, 1, &shouldAllocateBuffer, sizeof(shouldAllocateBuffer));
*/
status = AudioOutputUnitStart(audioUnit);

}
static OSStatus recordingCallback(void *inRefCon,
AudioUnitRenderActionFlags *ioActionFlags,
const AudioTimeStamp *inTimeStamp,
UInt32 inBusNumber,
UInt32 inNumberFrames,
AudioBufferList *ioData) {
AudioBuffer buffer;

buffer.mNumberChannels = 1;
buffer.mDataByteSize = inNumberFrames * 2;
//NSLog(@"%d",inNumberFrames);
buffer.mData = malloc( inNumberFrames * 2 );

// Put buffer in a AudioBufferList
AudioBufferList bufferList;
bufferList.mNumberBuffers = 1;
bufferList.mBuffers[0] = buffer;



OSStatus status;
status = AudioUnitRender(audioUnit,
ioActionFlags,
inTimeStamp,
inBusNumber,
inNumberFrames,
&bufferList);
checkStatus(status);
//double g = calculateGoertzel((const char *)(&bufferList)->mBuffers[0].mData,16789.0,96000.0);
UInt16 *q = (UInt16 *)(&bufferList)->mBuffers[0].mData;
int N = sizeof(q)/sizeof(UInt16);
double Qr,Qi;
double theta = 2.0*M_PI*16780/44100;
double g = goertzel(q,44100,16780,N);

NSLog(@"goertzel:%f", g);
}

对于远低于 16780Hz 的频率,这将返回以数百为单位的数字,对于 16780Hz 的频率,返回的数字要小得多。

我非常沮丧,非常感谢您的帮助。

最佳答案

只是一个猜测:

根据 Nyquist–Shannon 采样定理,采样率应至少是您要测量的频率的两倍。而你的是,但只是勉强。 44.1kHz 的采样率是测量 22kHz 信号的外缘。 16kHz 的信号足够接近混叠可能导致波形分析出现问题的极限。这是一张图片来说明我的观点: enter image description here

所以,我猜你需要更高的采样率。为什么不尝试通过算法运行一个纯 16kHz 正弦波,看看它是否做得更好?如果您在测试数据中只有一个频率,混叠将不是一个问题。如果您从正弦波获得更高的响应,那么您可能只需要更高的采样率。

关于iphone - 核心音频,Goertzel 算法不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5284412/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com