首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >检测音频零交叉的选项

检测音频零交叉的选项
EN

Stack Overflow用户
提问于 2015-12-23 19:48:22
回答 2查看 2.9K关注 0票数 2

我有现场音频进入,我需要发现零交叉。

这样做的简单算法,如this question所述,对于我所需的内容是不可接受的。该算法利用当前项与前一项相乘的符号检测过零点。

这是此方法失败的一个简单示例:

1,-0.5,0,0,0.32,0.5.

一排排两个零,算法就会失败。

此方法通过以下方式实现:

代码语言:javascript
运行
复制
int sign(float value) {
  if (value < 0) {
    return -1;
  } else if (value > 0) {
    return 1;
  }
  return 0;
}

for (int i=0; i<numFrames-1; i++) {
    int signR = sign(data[i+1] * data[i]);        
    if (signR == 0) printf("zero cross");
    // but this will fail for data[i+1] = data[i] = 0, for example

}

还有什么其他的算法选项,我必须检测零交叉吗?

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2015-12-23 21:42:33

忽略该值,只使用该标志检测交叉。

代码语言:javascript
运行
复制
#include <math.h>

for (int i=0; i<numFrames-1; i++) {
  if (signbit(data[i+1]) != signbit(data[i])) printf("zero cross");
}

signbit宏报告所有值的符号,包括无穷大、零和NaNs。

编辑

signbit()返回一个非零值当且仅当其参数值的符号为负值时。因此,两个不同的负值可能会返回不同的非零值。更好地使用:

代码语言:javascript
运行
复制
  if (!signbit(data[i+1]) != !signbit(data[i])) printf("zero cross");
票数 0
EN

Stack Overflow用户

发布于 2015-12-23 20:05:15

记录上一次非零样本的符号,如果当前样本也是非零的,则只考虑乘法的结果(零样本本身从不相交)。

代码语言:javascript
运行
复制
for (int i=0, previous=sign(data[0]); i<numFrames-1; i++) {
    if(int current = sign(data[i])) {
        if(sign(previous * current) == -1)
            printf("zero cross");
        previous = current;
    }
}
票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/34442710

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档