Java 从wav文件中提取频率
我试图从wav文件中提取频率,但看起来好像出了问题 首先,我从文件中提取字节,然后对其应用FFT,最后找到大小 似乎我做错了什么,因为输出不接近实际值。 下面是代码Java 从wav文件中提取频率,java,fft,Java,Fft,我试图从wav文件中提取频率,但看起来好像出了问题 首先,我从文件中提取字节,然后对其应用FFT,最后找到大小 似乎我做错了什么,因为输出不接近实际值。 下面是代码 try{ File log = new File("files/log.txt"); if(!log.exists()) log.createNewFile(); PrintStream ps = new PrintStream(log); File f = ne
try{
File log = new File("files/log.txt");
if(!log.exists()) log.createNewFile();
PrintStream ps = new PrintStream(log);
File f = new File("files/5000.wav");
FileInputStream fis = new FileInputStream(f);
int length = (int)f.length();
length = (int)nearestPow2(length);
double[] ibr = new double[length]; //== real
double[] ibi = new double[length]; //== imaginary
int i = 0;
int l=0;
//fis.skip(44);
byte[] b = new byte[1024];
while((l=fis.read(b))!=-1){
try{
for(int j=0; j<1024; j++){
ibr[i] = b[j];
ibi[i] = 0;
i++;
}
}catch(Exception e){}
}
double[] ftb = FFTBase.fft(ibr, ibi, true);
double[] mag = new double[ftb.length/2];
double mxMag = 0;
long avgMg = 0;
int reqIndex = 512; //== no need to go till end
for(i=1;i<ibi.length; i++){
ibr[i] = ftb[i*2];
ibi[i] = ftb[i*2+1];
mag[i] = Math.sqrt(ibr[i]*ibr[i]+ibi[i]*ibi[i]);
avgMg += mag[i];
if(mag[i]>mxMag) mxMag = mag[i];
ps.println(mag[i]);
}
avgMg = avgMg/ibi.length;
ps.println("MAx===="+mxMag);
ps.println("Average===="+avgMg);
}catch(Exception e){e.printStackTrace();}
试试看{
文件日志=新文件(“files/log.txt”);
如果(!log.exists())log.createNewFile();
PrintStream ps=新的PrintStream(日志);
文件f=新文件(“文件/5000.wav”);
FileInputStream fis=新的FileInputStream(f);
int length=(int)f.length();
长度=(int)最接近POW2(长度);
双精度[]ibr=新双精度[长度];//==实值
双精度[]ibi=新双精度[长度];//==虚拟
int i=0;
int l=0;
//财政司司长(44);
字节[]b=新字节[1024];
而((l=fis.read(b))!=-1){
试一试{
对于(int j=0;j提取一个频率或“音高”是不可能的,不幸的是,仅通过fft和搜索“最响亮”的频率或类似的东西。至少如果你试图从音乐信号中提取它
还有不同种类的音调。大部分乐器(如吉他或我们的声音)产生和声,这些和声由几个频率组成,这些频率遵循一定的模式
但也有一些音调只有一个峰值/频率(即口哨声)
此外,你通常必须处理信号中的噪声,而这些噪声根本不是音调。这可能是背景噪声,也可能是乐器本身产生的。例如,吉他在攻击阶段有很大的噪声部分
您可以使用不同的方法,即不同的算法来查找这些信号的基音,具体取决于其类型
如果我们停留在频域(fft)中,假设我们想要分析谐波声音,例如,双向失配算法
,它使用统计模式匹配来查找谐波并猜测基频
,这是我们耳朵感知为音调的频率
这里可以找到一个示例实现:此repo是coursera音频信号处理完整课程的一部分,也许这会有所帮助。}catch(例外e){}
← 永远不要写空的catch块。你应该完全删除try/catch。如果出现问题,你将无法知道。这是出于某种目的。您好,您所说的完全正确,但我正在测试的音频文件频谱平坦,因此我怀疑其中是否有峰值。但是在代码中,我得到了价值s不是常数。哦,对不起……说实话,我不明白你说的“找到震级”是什么意思。听起来你在寻找一个单一的震级值。在我的理解中是“震级”频谱上的y轴是否与fft一致,因此频谱中的每个箱子都会有一个大小。是的,如果频谱是平线,所有点的大小都会一样吗?或者至少应该足够近?如果wav文件中有完美的静音,那么我希望所有箱子的大小都为0。但是你在pastebin上的值包含指数298、298*2和298*3处的峰值…并非100%完美,但非常接近。在我看来,这是一个谐波。谐波的频率应为spampleRate/fftSize*298