5

私は現在困惑しています。私は周りを見回して、オーディオの比較を実験してきました。私はかなりの量の資料と、それを行うためのさまざまなライブラリとメソッドへの大量の参照を見つけました。

今のところ、 Audacityを使って「long.wav」という 3 分間の wav ファイルをエクスポートし、その最初の 30 秒を「short.wav」というファイルに分割しました。私は、それぞれのJavaを介してデータを視覚的にログ(log.txt)に記録でき、値の間で少なくともいくつかの視覚的な類似性を確認できるはずです....ここにいくつかのコードがあります

な方法:

        int totalFramesRead = 0;
        File fileIn = new File(filePath);
        BufferedWriter writer = new BufferedWriter(new FileWriter(outPath));
        writer.flush();
        writer.write("");
        try {
            AudioInputStream audioInputStream = 
                    AudioSystem.getAudioInputStream(fileIn);
            int bytesPerFrame = 
                    audioInputStream.getFormat().getFrameSize();
            if (bytesPerFrame == AudioSystem.NOT_SPECIFIED) {
                // some audio formats may have unspecified frame size
                // in that case we may read any amount of bytes
                bytesPerFrame = 1;
            } 
            // Set an arbitrary buffer size of 1024 frames.
            int numBytes = 1024 * bytesPerFrame; 
            byte[] audioBytes = new byte[numBytes];
            try {
                int numBytesRead = 0;
                int numFramesRead = 0;
                // Try to read numBytes bytes from the file.
                while ((numBytesRead = 
                        audioInputStream.read(audioBytes)) != -1) {
                    // Calculate the number of frames actually read.
                    numFramesRead = numBytesRead / bytesPerFrame;
                    totalFramesRead += numFramesRead;
                    // Here, do something useful with the audio data that's 
                    // now in the audioBytes array...

                    if(totalFramesRead <= 4096 * 100)
                    {                           

                    Complex[][] results = PerformFFT(audioBytes);
                    int[][] lines = GetKeyPoints(results);
                    DumpToFile(lines, writer);      

                    }   
                }
            } catch (Exception ex) { 
                // Handle the error...
            }
            audioInputStream.close();
        } catch (Exception e) {
            // Handle the error...
        }
        writer.close();

次に、PerformFFT :

public static Complex[][] PerformFFT(byte[] data) throws IOException
    {
        final int totalSize = data.length;

        int amountPossible = totalSize/Harvester.CHUNK_SIZE;

        //When turning into frequency domain we'll need complex numbers:
        Complex[][] results = new Complex[amountPossible][];

        //For all the chunks:
        for(int times = 0;times < amountPossible; times++) {
            Complex[] complex = new Complex[Harvester.CHUNK_SIZE];
            for(int i = 0;i < Harvester.CHUNK_SIZE;i++) {
                //Put the time domain data into a complex number with imaginary part as 0:
                complex[i] = new Complex(data[(times*Harvester.CHUNK_SIZE)+i], 0);
            }
            //Perform FFT analysis on the chunk:
            results[times] = FFT.fft(complex);
        }
            return results;
}

この時点で、変換前の audioBytes、Complex 値、FFT の結果など、あらゆる場所でログを記録してみました。

問題:どのような値をログに記録しても、各 wav ファイルの log.txt は完全に異なります。私はそれを理解していません。small.wav を large.wav から取得した (そしてそれらはすべて同じプロパティを持っている) ことを考えると、生の wav byte[] データまたは Complex[][] fft データのいずれかの間に非常に大きな類似性があるはずです。 ..またはこれまでの何か..

これらの計算のどの時点でもデータが似ていない場合、これらのファイル を比較するにはどうすればよいでしょうか。

私は音声分析に関してかなりの知識が欠けていることを知っています。これが私がボードに助けを求める理由です! 提供できる情報、ヘルプ、または修正をありがとう!!

4

5 に答える 5

2

MARFを見たことがありますか?これは、音声認識に使用される十分に文書化された Java ライブラリです。

これは話者を認識するために使用されますが (文字起こしまたはソフトウェアの保護のために)、同じ機能を使用して音声サンプルを分類できる必要があります。私はそれに慣れていませんが、 FeatureExtractionクラスを使用して、各オーディオ サンプルから特徴の配列を抽出し、一意の ID を作成したいようです。

于 2012-08-08T16:43:12.367 に答える
1

16 ビット オーディオの場合、3e-05 は 0 とそれほど違いはありません。したがって、ゼロのファイルはゼロのファイルとほとんど同じです (小さな丸め誤差によって等値が失われる可能性があります)。

追加: 比較のために、いくつかの Java プロット ライブラリを使用して、2 つの波形のそれぞれの部分を読み込んでプロットし、ほぼ (ほぼ) ゼロの部分を通過します。

于 2012-07-23T03:13:49.543 に答える
0

両方のオーディオファイルをどのように比較しているかわかりませんが、音楽認識を提供するサービス(TrackIdやMotoIDなど)を見ると、これらのサービスは、聞いている音楽の小さなサンプル(10〜20秒)を取得します。それらをサーバーで処理します。私は、それらが長さ以下のサンプルを持ち、そのサンプルのパターンのデータベース(またはその場で計算する)を持っていると理論付けています(あなたの場合はフーリエ変換)、あなたの場合、あなたは必要かもしれません長いオーディオファイルをサンプルデータ以下のチャンクに分割するには、最初のケースでは、サンプルデータのパターンに似た特定のチャンクを見つけることができます。後者の場合、小さなチャンクは、サンプルデータの一部をリサンブルすることがあります。サンプルデータと、サンプルデータがそれぞれのオーディオファイルに属する確率を計算できます。

于 2012-08-08T17:26:46.860 に答える
0

Acoustic Fingerprintingを見ていると思いますが 、それは難しく、それを行うためのライブラリがあります。自分で実装したい場合は、これがシャザム アルゴリズムに関するホワイトペーパーです。

于 2012-08-08T17:56:59.570 に答える