我有一个文件 input.mp3,在其上运行 ffprobe 会给出以下内容:
[mp3 @ 0x559431400a00] Estimating duration from bitrate, this may be inaccurate
Input #0, mp3, from '../backup/1.mp3':
Metadata:
album : DW01-The Colour Of Magic
artist : Terry Pratchett
album_artist : Terry Pratchett
comment : Read By Nigel Planer
composer : Nigel Planer
genre : Discworld
publisher : Polygram
title : Colour Of Magic 1 of 6
track : 1
date : 1983
id3v2_priv.WM/Provider: A\x00M\x00G\x00\x00\x00
id3v2_priv.WM/WMCollectionGroupID: \xe4\xbba\xf0\xf2\xcd.D\xab\x92b\xeb{\x8b\x9a\xce
id3v2_priv.WM/WMCollectionID: \xe4\xbba\xf0\xf2\xcd.D\xab\x92b\xeb{\x8b\x9a\xce
id3v2_priv.WM/UniqueFileIdentifier: A\x00M\x00G\x00a\x00_\x00i\x00d\x00=\x00R\x00 \x00 \x00 \x002\x007\x007\x008\x004\x003\x00;\x00A\x00M\x00G\x00p\x00_\x00i\x00d\x00=\x00P\x00 \x00 \x00 \x00 \x00 \x00 \x003\x003\x007\x00;\x00A\x00M\x00G\x00t\x00_\x00i\x00d\x00=\x00T\x00 \x00 \x001\x005\x00
id3v2_priv.WM/WMContentID: h\x86H@^\xe6qF\x95T\x04m\x01P\x90\x7f
id3v2_priv.WM/MediaClassSecondaryID: \x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00
id3v2_priv.WM/MediaClassPrimaryID: \xbc}`\xd1#\xe3\xe2K\x86\xa1H\xa4*(D\x1e
id3v2_priv.ZuneCollectionID: \x1d\xcb\xdf\xf3X89D\x81\xd1\xd0s#P\x00\xf8
Duration: 01:08:19.30, start: 0.000000, bitrate: 32 kb/s
Stream #0:0: Audio: mp3, 44100 Hz, stereo, fltp, 32 kb/s
Stream #0:1: Video: mjpeg (Baseline), yuvj420p(pc, bt470bg/unknown/unknown), 274x417, 90k tbr, 90k tbn, 90k tbc (attached pic)
Metadata:
comment : Cover (front)
我想对这个文件做很多事情,比如将它与其他文件连接起来,然后将它分成小段。但现在,我将只考虑删除元数据的简单情况,因为它本身会产生与我在其他操作中遇到的问题类似的问题。当我在上述文件上运行以下命令时:
ffmpeg -i input.mp3 -map 0:a -c:a copy -map_metadata -1 output.mp3
然后我在 output.mp3 上运行 ffprobe
Input #0, mp3, from 'output.mp3':
Metadata:
encoder : Lavf58.29.100
Duration: 01:08:19.27, start: 0.011995, bitrate: 32 kb/s
Stream #0:0: Audio: mp3, 44100 Hz, stereo, fltp, 32 kb/s
Metadata:
encoder : Lavf
为什么持续时间会减少 0.03 秒?为什么开始时间不再是0?另外,为什么当我在 vlc 中打开这个文件时,似乎无法确定持续时间?使用原始文件,它可以立即知道持续时间。但是对于新文件,它似乎在尝试估计它,随着我播放它的时间慢慢接近。
vlc 中的编解码器信息(两个文件都相同)
Stream 0
Codec: MPEG Audio layer 1/2 (mpga)
Type: Audio
Channels: Stereo
Sample rate: 44100 Hz
Bits per sample: 32
Bitrate: 32 kb/s
MP3 文件不具有与 MP4 或 MKV 文件相同的内部结构——“普通”MP3 只是一系列原始音频帧,其持续时间不存储在任何地方。对于恒定比特率的 MP3 文件,持续时间可以根据文件的长度计算,而对于 VBR,只能通过逐帧评估整个文件来确定。
也就是说,除非编码器将持续时间和 VBR 信息存储在“ LAME INFO 标签”(又名“Xing VBR 标签”)中。现在几乎所有的编码器和播放器都支持这个标签,大多数 MP3 文件都有它。
从 ffprobe 输出来看,您的原始文件似乎没有这样的标签,而新文件有(“编码器:Lavf”是其中的一部分,由 FFmpeg 添加)。所以我希望得到相反的结果——新文件的持续时间应该是已知的,但原始文件的持续时间应该是已知的——也就是说,除非 FFmpeg 添加了不准确的信息。
事实上,一个普通的 MP3 文件甚至没有为元数据保留任何空间——Xing 和 ID3 标签实际上伪装成大多数解码器知道要忽略的特殊音频帧——这也意味着 MP3 文件的估计持续时间可能取决于如何它包含或曾经包含的许多元数据。如果文件中有 ID3v2 标签删除后留下的空洞,则诸如“size÷bitrate”之类的简单估计将是错误的。
您可以使用Mp3Diags查看文件的结构。(它也可以用来修复不准确的 Xing 标签,这些标签会让玩家认为赛道比实际更长或更短。)
一个 mp3 文件包含三样东西:音频块、元数据和垃圾。音频播放器可能具有读取和显示元数据的代码,并且它必须具有播放音频块的代码。垃圾被忽略。
现在音频数据的显示长度已经改变。有两个可能的原因:
元数据编辑器设法破坏了音频块的标头(音频块通常约为 30 毫秒)。随着标题被破坏,音频块现在是垃圾,所以这实际上减少了音频长度。
音频播放器不会扫描所有音频块并将它们的持续时间相加,而是根据文件大小猜测音频块的数量。也许它没有考虑元数据,所以拥有更多的元数据会使它高估音频长度。由于您删除了元数据,因此减少了估计的音频长度。实际长度没有变化,可能比显示的要少。