如何从MP3文件中获取声道数?使用go-mp3库未果
获取MP3声道数的可行方案
针对github.com/hajimehoshi/go-mp3库没有直接获取声道数API的问题,这里提供两种实用解决办法:
办法一:手动解析MP3帧头
MP3的声道信息存储在音频帧的帧头里,我们可以跳过开头的ID3标签后,读取第一个帧头解析出声道数:
package main import ( "os" "github.com/hajimehoshi/go-mp3" ) func getMP3Channels(f *os.File) (int, error) { // 检查并跳过ID3v2标签 f.Seek(0, 0) var id3Buf [10]byte if _, err := f.Read(id3Buf[:]); err != nil { return 0, err } if string(id3Buf[:3]) == "ID3" { // 计算ID3标签的总大小(同步安全整数格式) size := int(id3Buf[6])<<21 | int(id3Buf[7])<<14 | int(id3Buf[8])<<7 | int(id3Buf[9]) if _, err := f.Seek(int64(10+size), 0); err != nil { return 0, err } } // 读取帧头前4字节 var frameBuf [4]byte if _, err := f.Read(frameBuf[:]); err != nil { return 0, err } // 解析帧头中的声道模式位 channelFlag := (frameBuf[1] >> 3) & 0x03 switch channelFlag { case 0, 1, 2: return 2, nil case 3: return 1, nil default: return 0, nil } } func main() { file, err := os.Open("example.mp3") if err != nil { panic(err) } defer file.Close() decoder, err := mp3.NewDecoder(file) if err != nil { panic(err) } defer decoder.Close() sampleRate := decoder.SampleRate() // 重新定位文件指针以解析声道数 file.Seek(0, 0) numChannels, err := getMP3Channels(file) if err != nil { panic(err) } }
办法二:换用支持元数据解析的音频库
如果不想手动处理帧头,可以使用go-audio/mp3库,它直接提供格式信息解析能力:
package main import ( "os" "github.com/go-audio/audio" "github.com/go-audio/mp3" ) func main() { file, err := os.Open("example.mp3") if err != nil { panic(err) } defer file.Close() decoder := mp3.NewDecoder(file) format := &audio.Format{} if err := decoder.FillFormat(format); err != nil { panic(err) } numChannels := format.NumChannels sampleRate := format.SampleRate }
这个库会自动处理ID3标签和帧头解析,直接返回声道数、采样率等格式参数。
内容的提问来源于stack exchange,提问作者ragarac3
相关产品推荐
相关产品推荐

