Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/apache-flex/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 如何从音频样本中确定频率的幅度和相位角?_Java_Audio_Signal Processing_Fft_Frequency - Fatal编程技术网

Java 如何从音频样本中确定频率的幅度和相位角?

Java 如何从音频样本中确定频率的幅度和相位角?,java,audio,signal-processing,fft,frequency,Java,Audio,Signal Processing,Fft,Frequency,我目前正在从事这个项目,这意味着一些DSP技能。 我必须从电影中提取音频,然后通过分析它,我必须确定某人何时说话,更像是语音活动检测器 我正在用Java编写代码(是的,我知道这不是最好的选择),只使用库从视频和JLayer中提取音频,这样我就可以处理MP3了 获取每个通道的连续采样,在我的示例中是两个:LEFT0、RIGHT0、LEFT1、RIGHT1、LEFT2、RIGHT2等 这就是我到目前为止所做的: 我将每个通道的样本放入一个数组中 我应用汉明窗[N=8192]: double w=0

我目前正在从事这个项目,这意味着一些DSP技能。 我必须从电影中提取音频,然后通过分析它,我必须确定某人何时说话,更像是语音活动检测器

我正在用Java编写代码(是的,我知道这不是最好的选择),只使用库从视频和JLayer中提取音频,这样我就可以处理MP3了

获取每个通道的连续采样,在我的示例中是两个:LEFT0、RIGHT0、LEFT1、RIGHT1、LEFT2、RIGHT2等

这就是我到目前为止所做的:

  • 我将每个通道的样本放入一个数组中
  • 我应用汉明窗[N=8192]:
    double w=0.54-0.46*(Math.cos(2*Math.PI*buffer[i]/buffer.length-1))
    
    fftBuffer[i]=新络合物(w,0)
  • 然后,我在每个通道上,计算振幅
    mag=re^2+im^2之后,我做一个对数标度(dB):
    mag_dB=10*log10(abs(mag))
因为我在这里“寻找声音”,所以我需要80到1000之间的频率(即使声音范围在80到255赫兹之间)。所以,从FFT中,我得到一个镜像的N=8129阵列,我只需要第一个N/2

每个仓的频率(FFT产生的阵列中的槽)将是采样率(48.000 kHz) /N;这将是48000/8192=每箱5赫兹。所以我只看数组中从FFT_结果[15]到FFT_结果[199]的值(16*5Hz=80 Hz;200*5=1000 Hz),对吗

我在Cool Edit Pro中查看了频率分析器,所有振幅都为负值。在我的例子中,第一个(声音在背景中,声音不是很大)是负面的,然后,它们都是正面的。他们不应该是消极的吗?我是不是错过了什么

到目前为止,根据我在Cool Edit Pro中通过查看频率分析器和相位分析器所做的评论,我需要一个该频率范围的阈值,某种算法,以确定在n毫秒的时间内,幅度在该频率范围内是否恒定,并确定声音是否居中。最后一个必须分析相位角,当有人说话时,声音总是居中的

我没有找到一种方法来做到这一点,我对我目前所做的一切感到困惑,因为我不知道我目前所做的是否正确

因此,如果您阅读了所有这些,感谢您的耐心,我的问题是:
-到目前为止我做的对吗?
-振幅必须为负吗?

-有人知道如何计算多个样本的相位吗?

在dB中,振幅可以是负的,也可以是正的,这无关紧要。重要的是相对于某个阈值的值。我会根据周围的样本来确定阈值。因为随着音节的发音,口语中的能量会上下波动,所以一个简单的平均值(乘以一些你必须使用的任意因子,才能找到合适的值)可以作为一个阈值


对于时域中的相位,您可以首先进行希尔伯特变换,然后对每个样本的实部和虚部使用atan2来估计瞬时相位。

您可以检查两个通道之间的延迟,而不是查看单个通道的相位。假设向两个通道提供相同的信号,则可以从通道间延迟中找到声源的方向。假设耳对耳距离约为20cm,此延迟最多为.2/340=.58ms,或在48kHz时约30个样本。如果计算该范围内的互相关(30个样本),则应找到指示震源方向的峰值


要找到类似声音的信号,可以计算80-1000Hz频带内的总能量,并根据某个合理的值设置阈值。您可以在频率域中通过将存储箱中的震级从80到1000Hz相加来实现这一点,或者在时域中使用带式滤波器和RMS值计算来实现这一点

您有一个双面变换。中点是直流分量。负频率实际上是一个正频率,相位相差180度!因此,如果使用FFT值的前半部分w/负频率,则需要通过pi改变相位,以准确地了解正在发生的情况

或者,在频率为正且相位正确的情况下,使用FFT值的后半部分

我看了一下Cool Edit Pro中的频率分析器和所有 振幅为负。在我的例子中,第一个(声音在 背景和声音)是负面的,然后是负面的 都是肯定的。他们不应该是消极的吗?我错过了吗 这里有什么


振幅为负?这是没有意义的,除了在分贝尺度上。是这样吗?@Oli Charlesworth:在我做对数刻度后,我得到如下值:6.192286815256956 1.4657064018498-2.360496921728435 4.294669805664844-2.2876799531445684-11.729105860184267.070140033122966正负混合together@Cyupa:哦,我错过了你问题中提到日志的那部分。很抱歉但是它们是正的还是负的完全是任意的,因为这取决于音频波形的整体比例。您可能想寻找的是振幅的显著相对变化,而不是特定的绝对水平。@奥利·查尔斯沃思:因此,您建议,根据某些频率单元振幅的先前值,我应该确定是否存在相对变化,而不是检查它是否达到某个值。谢谢你的建议。:-)@Cyupa:是的,可能是相对于上一时间点的bin值。或者相对于该时间间隔内整个FFT的平均bin值。有效地,计算机