Python音频处理库 pydub
Pydub lets you do stuff to audio in a way that isn’t stupid。
**Pydub:**处理音频文件,但是Pydub只支持原生的wav格式的文件处理。如果想处理其他格式的音频,或者说想处理媒体文件中的音频那需要在本地安装FFmpeg支持。
安装ffmpeg
安装Pydub
pip install pydub
使用
cat <<EOF | tee /home/iray/work/code/temp/pydub_video.py
from pydub import AudioSegment
import os
import sys
path = os.getcwd()
def file_exists(file_path):
if os.path.isfile(os.path.join(path,file_path)):
return os.path.join(path,file_path)
elif os.path.isfile(file_path):
return file_path
else:
return False
# 从视频文件保存音轨
def convert_video(file_path):
mp3_filename = os.path.splitext(os.path.basename(file_path))[0] + '.mp3'
AudioSegment.from_file(file_path).export(mp3_filename, format='mp3')
# 音频文件截取
def cut_audio(file_path, start_second):
song = AudioSegment.from_mp3(file_path)
start_millsecond = start_second * 1000
song[start_millsecond:].export(file_path)
if __name__ == '__main__':
file_path = file_exists(sys.argv[1])
start_second = int(sys.argv[2])
if file_path:
cut_audio(file_path, start_second)
print("文件转换成功")
else:
print("文件路径错误!")
input("按任意键退出\n")
EOF
# 执行
python3 pydub_video.py "/home/iray/file_path.mp3" 75
打开一个wav
文件
from pydub import AudioSegment
song = AudioSegment.from_wav("never_gonna_give_you_up.wav")
打开一个mp3
文件
song = AudioSegment.from_mp3("never_gonna_give_you_up.mp3")
或者一个ogg
或者flv
,或者其他所有ffmpeg支持的格式
ogg_version = AudioSegment.from_ogg("never_gonna_give_you_up.ogg")
flv_version = AudioSegment.from_flv("never_gonna_give_you_up.flv")
mp4_version = AudioSegment.from_file("never_gonna_give_you_up.mp4", "mp4")
wma_version = AudioSegment.from_file("never_gonna_give_you_up.wma", "wma")
aac_version = AudioSegment.from_file("never_gonna_give_you_up.aiff", "aac")
切片音频:
# pydub does things in milliseconds
ten_seconds = 10 * 1000
first_10_seconds = song[:ten_seconds]
last_5_seconds = song[-5000:]
让开始更响亮,结束更安静
# boost volume by 6dB
beginning = first_10_seconds + 6
# reduce volume by 3dB
end = last_5_seconds - 3
连接音频即声音合成(将一个文件添加到另一个文件的末尾)
without_the_middle = beginning + end
查看音屏有多长时间?
without_the_middle.duration_seconds == 15.0
audiosegments
是不变的
# song is not modified
backwards = song.reverse()
交叉淡入淡出(再次,开始和结束都不会被修改)
# 1.5 second crossfade
with_style = beginning.append(end, crossfade=1500)
重复音频(重复追加生成一个文件)
# repeat the clip twice
do_it_over = with_style * 2
淡入淡出(请注意,您可以链接操作,因为一切都返回一个AudioSegment
)
# 2 sec fade in, 3 sec fade out
awesome = do_it_over.fade_in(2000).fade_out(3000)
保存结果(所有ffmpeg
支持的都支持)
awesome.export("mashup.mp3", format="mp3")
用标签保存结果(元数据)
awesome.export("mashup.mp3", format="mp3", tags={'artist': 'Various artists', 'album': 'Best of 2011', 'comments': 'This album is awesome!'})
您可以传递一个可选的比特率参数来使用ffmpeg支持的所有语法进行输出。
awesome.export("mashup.mp3", format="mp3", bitrate="192k")
所有ffmpeg
支持的进一步的参数都可以在参数中以列表形式传递,其中第一个参数是转变论证第二。请注意,这些参数不会进行验证,而且您可能受到ffmpeg/avlib
支持的特定版本的限制。
# Use preset mp3 quality 0 (equivalent to lame V0)
awesome.export("mashup.mp3", format="mp3", parameters=["-q:a", "0"])
# Mix down to two channels and set hard output volume
awesome.export("mashup.mp3", format="mp3", parameters=["-ac", "2", "-vol", "150"])
调试
人们遇到的大多数问题都与使用ffmpeg/avlib
格式之间的转换有关。Pydub
提供了一个输出子进程调用的记录器来帮助您追踪问题:
>>> import logging
>>> l = logging.getLogger("pydub.converter")
>>> l.setLevel(logging.DEBUG)
>>> l.addHandler(logging.StreamHandler())
>>> AudioSegment.from_file("./test/data/test1.mp3")
subprocess.call(['ffmpeg', '-y', '-i', '/var/folders/71/42k8g72x4pq09tfp920d033r0000gn/T/tmpeZTgMy', '-vn', '-f', 'wav', '/var/folders/71/42k8g72x4pq09tfp920d033r0000gn/T/tmpK5aLcZ'])
<pydub.audio_segment.AudioSegment object at 0x101b43e10>
不要担心在转换中使用的临时文件,他们会自动清理。
Ogg
导出和默认编解码器
如果没有指定编解码器导出到ogg
会默认使用vorbis
的convinence
。那是:
from pydub import AudioSegment
song = AudioSegment.from_mp3("test/data/test1.mp3")
song.export("out.ogg", format="ogg") # Is the same as:
song.export("out.ogg", format="ogg", codec="libvorbis")
使用示例
假如你有一个mp4
和flv
视频的目录,并且你想把它们全部转换成mp3
,所以你可以在你的mp3
播放器上聆听它们。
import os
import glob
from pydub import AudioSegment
video_dir = '/home/johndoe/downloaded_videos/' # Path where the videos are located
extension_list = ('*.mp4', '*.flv')
os.chdir(video_dir)
for extension in extension_list:
for video in glob.glob(extension):
mp3_filename = os.path.splitext(os.path.basename(video))[0] + '.mp3'
AudioSegment.from_file(video).export(mp3_filename, format='mp3')
另一个例子
from glob import glob
from pydub import AudioSegment
playlist_songs = [AudioSegment.from_mp3(mp3_file) for mp3_file in glob("*.mp3")]
first_song = playlist_songs.pop(0)
# let's just include the first 30 seconds of the first song (slicing
# is done by milliseconds)
beginning_of_song = first_song[:30*1000]
playlist = beginning_of_song
for song in playlist_songs:
# We don't want an abrupt stop at the end, so let's do a 10 second crossfades
playlist = playlist.append(song, crossfade=(10 * 1000))
# let's fade out the end of the last song
playlist = playlist.fade_out(30)
# hmm I wonder how long it is... ( len(audio_segment) returns milliseconds )
playlist_length = len(playlist) / (1000*60)
# lets save it!
out_f = open("%s_minute_playlist.mp3" % playlist_length, 'wb')
playlist.export(out_f, format='mp3')
简单应用
从视频文件保存音轨
from pydub import AudioSegment
import os
import sys
path = os.getcwd()
def file_exists(file_path):
if os.path.isfile(os.path.join(path,file_path)):
return os.path.join(path,file_path)
elif os.path.isfile(file_path):
return file_path
else:
return False
def convert_video(file_path):
mp3_filename = os.path.splitext(os.path.basename(file_path))[0] + '.mp3'
AudioSegment.from_file(file_path).export(mp3_filename, format='mp3')
if __name__ == '__main__':
file_path = file_exists(sys.argv[1])
if file_path:
convert_video(file_path)
print("文件转换成功")
else:
print("文件路径错误!")
input("按任意键退出\n")
在Terminal输入:python convert.py "文件路径或当前路径下文件名"
,完成之后就可以在目录下看到输出的MP3文件。
实现音频倒放
from pydub import AudioSegment
# 读取被转换的音频文件
temp = AudioSegment.from_file(f"那就晚安.m4a")
# 通过 export 将其转换为目标格式文件
temp.export("那就晚安.mp3")
# 顺便将其倒放
backplay = temp.reverse()
# 存为相关格式倒放文件
backplay.export(f"倒放.mp3")
Q.E.D.