split_audio_with_overlap.py ダウンロード/コピー

split_audio_with_overlap.py をダウンロード

split_audio_with_overlap.py
split_audio_with_overlap.py
  1"""
  2概要:
  3    長い音声ファイルを指定された最大サイズでオーバーラップ付きで分割するスクリプト。
  4
  5詳細説明:
  6    このスクリプトは、入力された音声ファイルを、コマンドライン引数またはスクリプト内の設定で指定された
  7    最大ファイルサイズ(メガバイト)に基づき、固定長のチャンクに分割します。
  8    分割時、連続するチャンク間には指定された秒数のオーバーラップを設けます。
  9    これにより、音声の途切れを防ぎ、連続再生がスムーズになるように設計されています。
 10    出力ファイルは連番で、入力ファイルと同じディレクトリ内の "split_fixed" サブディレクトリに保存されます。
 11
 12引数:
 13    このスクリプトは以下のコマンドライン引数を受け取ります。
 14    各引数は指定されない場合、スクリプト内のデフォルト値が適用されます。
 15    
 16    input_audio_file: 分割対象の音声ファイルパス。(必須)
 17    output_format: 出力ファイルのフォーマット(例: mp3, wav)。デフォルトは mp3。
 18    bitrate: 出力ファイルのビットレート(例: 128k)。デフォルトは 128k。
 19    max_size_mb: 1チャンクあたりの最大サイズ(MB)。デフォルトは 150.0。
 20    overlap_sec: チャンク間のオーバーラップ時間(秒)。デフォルトは 60.0。
 21
 22関連リンク:
 23    split_audio_with_overlap_usage
 24"""
 25import os
 26import sys
 27from pydub import AudioSegment
 28
 29# ====== 設定 ======
 30output_dir = "split_fixed"
 31output_format = "mp3"           # 出力形式("mp3", "wav"など)
 32bitrate = "128k"                # 出力ビットレート
 33max_size_mb = 150               # チャンク最大サイズ(MB)
 34overlap_sec = 60                # オーバーラップ時間(秒)
 35
 36# ====== 引数処理 ======
 37if len(sys.argv) < 2:
 38    print("使い方: python fixed_split.py <input_audio_file>")
 39    sys.exit(1)
 40
 41input_file = sys.argv[1] # 必須引数
 42
 43nargs = len(sys.argv)
 44# 引数がある場合のみ、デフォルト値を上書き
 45if nargs > 2: output_format = sys.argv[2]
 46if nargs > 3: bitrate = sys.argv[3]
 47if nargs > 4: max_size_mb = float(sys.argv[4])
 48if nargs > 5: overlap_sec = float(sys.argv[5])
 49
 50if not os.path.isfile(input_file):
 51    print(f"エラー: ファイルが見つかりません: {input_file}")
 52    sys.exit(1)
 53
 54# ====== 音声読み込み ======
 55ext = os.path.splitext(input_file)[1].lower().lstrip(".")
 56print(f"\n音声ファイルを読み込み中...: {input_file} (.{ext})")
 57audio = AudioSegment.from_file(input_file, format=ext)
 58duration_sec = len(audio) // 1000
 59
 60# ====== 処理情報出力 ======
 61print(f"出力ディレクトリ: {output_dir}")
 62print(f"出力フォーマット: {output_format}")
 63print(f"ビットレート: {bitrate}")
 64print(f"オーバーラップ長: {overlap_sec}秒")
 65print(f"最大サイズ: {max_size_mb}MB")
 66print(f"音声長さ: {duration_sec} 秒")
 67
 68# ====== 出力ディレクトリ準備 ======
 69dir = os.path.dirname(input_file)
 70output_dir = os.path.join(dir, output_dir)
 71print("output_dir:", output_dir)
 72if not os.path.exists(output_dir):
 73    os.makedirs(output_dir, exist_ok=True)
 74
 75# ====== チャンク長(秒)の見積もり ======
 76kbps = int(bitrate.replace("k", ""))
 77bytes_per_sec = kbps * 1000 // 8
 78max_bytes = max_size_mb * 1024 * 1024
 79max_chunk_sec = max_bytes // bytes_per_sec
 80step = max_chunk_sec - overlap_sec  # オーバーラップを考慮した前進幅
 81
 82print(f"推定チャンク長: 約 {max_chunk_sec} 秒(@{bitrate})")
 83print(f"ステップ(次の開始位置): {step} 秒(オーバーラップ {overlap_sec} 秒)")
 84print(f"\n分割開始: 約{max_chunk_sec}秒ごとに分割({overlap_sec}秒の重なりあり)")
 85
 86# ====== 分割処理 ======
 87chunk_index = 0
 88start_sec = 0
 89filebody = os.path.splitext(os.path.basename(input_file))[0]
 90
 91while start_sec < duration_sec:
 92    print(f"> チャンク {chunk_index + 1} 開始: {start_sec}秒") 
 93    end_sec = start_sec + max_chunk_sec
 94    end_sec = min(end_sec, duration_sec)  # 終端を超えない
 95
 96    # 切り出し(ミリ秒)
 97    start_ms = start_sec * 1000
 98    end_ms = end_sec * 1000
 99    chunk = audio[start_ms:end_ms]
100
101    # ファイル保存
102    out_path = os.path.join(output_dir, f"{filebody}_{chunk_index:03}.{output_format}")
103    chunk.export(out_path, format=output_format, bitrate=bitrate)
104    print(f"> 保存: {out_path}{(end_sec - start_sec)} 秒)")
105
106    # 次の位置へ進む(オーバーラップ考慮)
107    start_sec += step
108    chunk_index += 1
109
110print("\n✅ サイズベースでオーバーラップ付き分割を完了しました。")
111input("\nPress ENTER to terminate>>\n")