Python
 Computer >> コンピューター >  >> プログラミング >> Python

Pythonで長い音声ファイルを文字起こしする方法!PydubとSpeechRecognitionによる音声分割・認識の完全ガイド

このチュートリアルでは、Pythonを使って音声ファイルを処理する方法を学びます。具体的には、長い音声ファイルを小さなチャンク(断片)に分割し、それぞれのチャンクから内容を認識してテキスト化します。最終的に、認識した内容はテキストファイルとして保存できます。

まず始めに、以下のコマンドで必要なモジュールをインストールしましょう。

必要なモジュールのインストール

pydub のインストール

pip install pydub

上記コマンドを実行すると、次のような成功メッセージが表示されます。

Collecting pydub
Downloading https://files.pythonhosted.org/packages/79/db/eaf620b73a1eec3c8c6f8f5b0b236a50f9da88ad57802154b7ba7664d0b8/pydub-0.23.1-py2.py3-none-any.whl
Installing collected packages: pydub
Successfully installed pydub-0.23.1

audioread のインストール

pip install audioread

こちらも同様に、正常に完了すると成功メッセージが表示されます。

Collecting audioread
Downloading https://files.pythonhosted.org/packages/2e/0b/940ea7861e0e9049f09dcfd72a90c9ae55f697c17c299a323f0148f913d2/audioread-2.1.8.tar.gz
Building wheels for collected packages: audioread
Building wheel for audioread (setup.py): started
Building wheel for audioread (setup.py): finished with status 'done'
Successfully built audioread
Installing collected packages: audioread
Successfully installed audioread-2.1.8

SpeechRecognition のインストール

pip install SpeechRecognition

実行後、以下のようにインストールが完了すれば準備OKです。

Collecting SpeechRecognition
Downloading https://files.pythonhosted.org/packages/26/e1/7f5678cd94ec1234269d23756dbdaa4c8cfaed973412f88ae8adf7893a50/SpeechRecognition-3.8.1-py2.py3-none-any.whl (32.8MB)
Installing collected packages: SpeechRecognition
Successfully installed SpeechRecognition-3.8.1

処理の全体像

今回の音声認識処理は、大きく分けて2つのステップで構成されています。

  • 音声ファイルを適切なサイズのチャンクに分割する
  • SpeechRecognition を使って各チャンクからテキストを抽出する

それでは、手持ちの音声ファイル(WAV形式)を用意して、実際にコードを書いていきましょう。なお、Google音声認識APIはインターネット接続が必要なので、ネットワーク環境にも注意してください。

サンプルコード

# モジュールのインポート
import pydub
import speech_recognition

# 音声ファイルを読み込む
audio = pydub.AudioSegment.from_wav('audio.wav')

# 音声の長さをミリ秒単位で取得
audio_length = len(audio)
print(f'Audio Length: {audio_length}')

# チャンク番号のカウンター
chunk_counter = 1

# 結果を書き込むテキストファイルを開く
audio_text = open('audio_text.txt', 'w+')

# どこで音声を切り出すかを設定
point = 60000   # 1回に切り出す長さ(60秒)

# オーバーラップ量(切り出し後に残す前チャンクとの重なり)
rem = 8000

# チャンク処理と終了判定のための変数を初期化
flag = 0
start = 0
end = 0

# remずつ重ねながら音声全体を走査
for i in range(0, 2 * audio_length, point):
    # 最初のループでは end = point となる
    if i == 0:
        start = 0
        end = point
    else:
        # 2回目以降のループ
        start = end - rem
        end = start + point
    # 終了位置が音声の長さを超えた場合
    if end >= audio_length:
        end = audio_length
        # 停止フラグを立てる
        flag = 1
    # 音声からチャンクを切り出す
    chunk = audio[start:end]
    # チャンク名を生成
    chunk_name = f'chunk_{chunk_counter}'
    # チャンクをローカルに保存
    chunk.export(chunk_name, format='wav')
    # 切り出した範囲を表示
    print(f'{chunk_name} start: {start} end: {end}')
    # チャンクカウンターを増やす
    chunk_counter += 1
    
    # 音声からテキストを認識する
    # 認識器(recognizer)を初期化
    recognizer = speech_recognition.Recognizer()
    # チャンク音声を読み込む
    with speech_recognition.AudioFile(chunk_name) as chunk_audio:
        chunk_listened = recognizer.listen(chunk_audio)
    # 音声の内容を認識
    try:
        # チャンクからテキストを取得
        content = recognizer.recognize_google(chunk_listened)
        # ファイルに書き込む
        audio_text.write(content + '\n')
    # 認識できなかった場合
    except speech_recognition.UnknownValueError:
        print('Audio is not recognized')
    # インターネット接続エラーの場合
    except speech_recognition.RequestError as Error:
        print("Can't connect to the internet")
    # 停止フラグをチェック
    if flag == 1:
        audio_text.close()
    break

実行結果

上記のコードを実行すると、次のような出力が得られます。音声が約48万ミリ秒(約8分)だったため、10個のチャンクに分割されました。

Audio Length: 480052
chunk_1 start: 0 end: 60000
chunk_2 start: 52000 end: 112000
chunk_3 start: 104000 end: 164000
chunk_4 start: 156000 end: 216000
chunk_5 start: 208000 end: 268000
chunk_6 start: 260000 end: 320000
chunk_7 start: 312000 end: 372000
chunk_8 start: 364000 end: 424000
chunk_9 start: 416000 end: 476000
chunk_10 start: 468000 end: 480052

注目ポイントとして、隣接するチャンク同士が8秒(8000ミリ秒)重なっていることがわかります。このオーバーラップにより、単語やフレーズがチャンク境界で途切れても、認識精度の低下を防げます。

認識結果の確認

次に、保存されたテキストファイルの中身を確認してみましょう。

# ファイルを読み取りモードで開く
with open('audio_text.txt', 'r') as file:
    print(file.read())

このコードを実行すると、以下のような認識結果が出力されます。

English and I am here in San Francisco I am back in San Francisco last week we were
in Texas at a teaching country and The Reader of the teaching conference was a plan
e Re
improve teaching as a result you are
house backup file with bad it had some
English is coming soon one day only time
12 o1 a.m.
everything about her English now or powering on my email list
sports in your city check your email email
Harjeet girlfriend
next Tuesday
checking the year enjoying office English keep listening keep smiling keep enjoying
your English learning

このように、音声ファイルの内容が自動的にテキストとして書き出されました。ただし、認識精度は音声の明瞭さや話し方によって左右されるため、一部の文が正確に変換されない場合もあります。ノイズの少ないクリアな音源を使うことで、より高い精度が期待できます。

まとめ

今回は、pydubで音声ファイルをオーバーラップ付きのチャンクに分割し、SpeechRecognitionライブラリ経由でGoogle音声認識APIを呼び出して文字起こしする手法を紹介しました。長時間の音声データを扱う際には、このような分割処理が非常に有効です。応用すれば、会議の議事録作成やポッドキャストの文字起こしなど、さまざまな場面で活用できるでしょう。

このチュートリアルについてご不明な点がある場合は、コメント欄でお気軽にお尋ねください。

  1. PythonのNews APIでトップニュースを取得する方法【サンプルコード付き】

    News APIは、世界中のニュースサイトから記事を検索・取得できる非常に有名なAPIです。このAPIを利用すれば、任意のニュースサイトから最新のトップニュースの見出しを簡単に取得できます。 ただし、News APIを使うにはAPIキーが必要です。APIキーはNews API公式サイトで無料登録すると発行できますので、事前に取得しておきましょう。 サンプルコード:BBCのトップニュースを取得する 以下は、Pythonのrequestsライブラリを使って、BBC Newsのトップニュースの見出しを番号付きで表示するサンプルコードです。 import requests def top_new

  2. MacでPython 3にアップグレードして使いこなす方法

    購入したばかりの新しいMacには、必要なソフトウェアの最新版がすべて入っていると思いがちですが、ユーザー向けアプリについては概ね正しくても、基盤となるフレームワークに関しては話が別です。安定版の最新リリースがPython 3.5であるにもかかわらず、新しいMacには今なおPython 2.7.10がプリインストールされています。バージョン間の差が大きく感じられるのはそのためです。ただし、新しいバージョンが必ずしも優れているとは限りません。Python 3はPython 2との後方互換性を持たず、多くの開発者は依然としてPython 2を使い続けているのです。 2to3を使うか、使わないか?