Python IMA ADPCM编解码器
我正在开发小型流媒体音频应用程序,audiochat客户端。服务器使用IMA ADPCM音频编解码器,帧速率8000,帧大小256字节 我正在使用描述的算法Python IMA ADPCM编解码器,python,audio,Python,Audio,我正在开发小型流媒体音频应用程序,audiochat客户端。服务器使用IMA ADPCM音频编解码器,帧速率8000,帧大小256字节 我正在使用描述的算法 参考压缩声音 解码声音的质量较差,服务器无法将编码声音识别为正确的ima adpcm声音 请帮我找出代码中的问题 # -*- coding: Utf-8 -*-t import wave, struct indexTable=[ -1, -1, -1, -1, 2, 4, 6, 8, -
参考压缩声音 解码声音的质量较差,服务器无法将编码声音识别为正确的ima adpcm声音 请帮我找出代码中的问题
# -*- coding: Utf-8 -*-t
import wave, struct
indexTable=[
-1, -1, -1, -1, 2, 4, 6, 8,
-1, -1, -1, -1, 2, 4, 6, 8
]
stepsizeTable=[
7, 8, 9, 10, 11, 12, 13, 14,
16, 17, 19, 21, 23, 25, 28, 31,
34, 37, 41, 45, 50, 55, 60, 66,
73, 80, 88, 97, 107, 118, 130, 143,
157, 173, 190, 209, 230, 253, 279, 307,
337, 371, 408, 449, 494, 544, 598, 658,
724, 796, 876, 963, 1060, 1166, 1282, 1411,
1552, 1707, 1878, 2066, 2272, 2499, 2749, 3024,
3327, 3660, 4026, 4428, 4871, 5358, 5894, 6484,
7132, 7845, 8630, 9493, 10442, 11487, 12635, 13899,
15289, 16818, 18500, 20350, 22385, 24623, 27086, 29794,
32767
]
def pcm2adpcm(frame): #frame - 1024 Bytes uncompressed
indexcode = 0
stepsizecode = 7
global indexTable
global stepsizeTable
predictedSample = 0
lstres=list()
for i in range(0,len(frame)): # Taking bytes
if (i+1)%2==0:
binsample=frame[i-1:i+1:]
originalsample=struct.unpack('h',binsample)[0] # To signed int
difference = originalsample-predictedSample
if difference>=0:
newSampleCode=0
else:
newSampleCode=8
difference=-difference
mask=4
tempStepsize=stepsizecode
for i in range(0,3):
if difference>=tempStepsize:
newSampleCode|=mask
difference-=tempStepsize
tempStepsize>>=1
mask>>=1
lstres.append(newSampleCode)
difference=0
if newSampleCode&4:
difference+=stepsizecode
if newSampleCode&2:
difference+=stepsizecode>>1
if newSampleCode&1:
difference+=stepsizecode>>2
difference+=stepsizecode>>3
if newSampleCode&8:
difference=-difference
predictedSample+=difference
if predictedSample>32767:
predictedSample=32767
if predictedSample<-32767:
predictedSample=-32767
indexcode+=indexTable[newSampleCode]
if indexcode<0:
indexcode=0
elif indexcode>88:
indexcode=88
stepsizecode=stepsizeTable[indexcode]
resultBinary=''
for i in range(0,len(lstres)):
if (i+1)%2==0:
#print lstres[i], lstres[i-1], (lstres[i]<<4)|lstres[i-1]
resultBinary+=chr((lstres[i]<<4)|lstres[i-1])
return resultBinary
def adpcm2pcm(frame): #frame - 256 Bytes compressed
index = 0
stepsize = 7
global indexTable
global stepsizeTable
newSample = 0
resultBinary=''
for i in range(0,len(frame)): # Taking bytes
binsample=frame[i]
originalsample=ord(frame[i]) #
secoundsample=originalsample>>4 # Secound 4 bit sample
firstsample=(secoundsample<<4)^originalsample # first 4 bit sample
lst=[firstsample,secoundsample] # To list
for originalsample in lst:
difference=0
if originalsample & 4:
difference+=stepsize
if originalsample & 2:
difference+=stepsize >> 1
if originalsample & 1:
difference+=stepsize >> 2
difference+=stepsize >> 3
if originalsample & 8:
difference=-difference
newSample+=difference
if newSample>32767:
newSample=32767
elif newSample<-32767:
newSample=-32767
resultBinary+=struct.pack('h',newSample)
index+=indexTable[originalsample]
if index<0:
index = 0
elif index>88:
index = 88
stepsize=stepsizeTable[index]
return resultBinary
if __name__ == '__main__':
#===========================================================================
# fout=wave.open('res.wav', 'wb')
# fout.setnchannels(1)
# fout.setsampwidth(2)
# fout.setframerate(8000)
# f=open('1.wav','rb')
# f.seek(60)
# for i in range (0,153):
# out=adpcm2pcm(f.read(256))
# fout.writeframesraw(out)
# fout.close()
#===========================================================================
f=open('1.wav','rb')
header=f.read(60)
foutcompr=open('resCompr.wav','wb')
foutcompr.write(header)
fout=wave.open('res.wav', 'rb')
n=0
while n<fout.getnframes():
foutcompr.write(pcm2adpcm(fout.readframes(512)))
n+=512
foutcompr.close()
print "finish"
#-*-编码:Utf-8-*-t
导入波,结构
不可名状=[
-1, -1, -1, -1, 2, 4, 6, 8,
-1, -1, -1, -1, 2, 4, 6, 8
]
阶梯形=[
7, 8, 9, 10, 11, 12, 13, 14,
16, 17, 19, 21, 23, 25, 28, 31,
34, 37, 41, 45, 50, 55, 60, 66,
73, 80, 88, 97, 107, 118, 130, 143,
157, 173, 190, 209, 230, 253, 279, 307,
337, 371, 408, 449, 494, 544, 598, 658,
724, 796, 876, 963, 1060, 1166, 1282, 1411,
1552, 1707, 1878, 2066, 2272, 2499, 2749, 3024,
3327, 3660, 4026, 4428, 4871, 5358, 5894, 6484,
7132, 7845, 8630, 9493, 10442, 11487, 12635, 13899,
15289, 16818, 18500, 20350, 22385, 24623, 27086, 29794,
32767
]
def pcm2adpcm(帧):#帧-1024字节未压缩
indexcode=0
stepsizecode=7
全局可索引
全局可分级
predictedSample=0
lstres=list()
对于范围(0,len(frame))中的i:#取字节
如果(i+1)%2==0:
binsample=帧[i-1:i+1:]
originalsample=struct.unpack('h',binsample)[0]#到带符号整数
差异=原始样本预测样本
如果差值>=0:
newSampleCode=0
其他:
newSampleCode=8
差异=-差异
掩码=4
tempStepsize=stepsizecode
对于范围(0,3)内的i:
如果差异>=tempStepsize:
newSampleCode |=掩码
差异-=步长
tempStepsize>>=1
掩码>>=1
lstres.append(newSampleCode)
差=0
如果newSampleCode&4:
差值+=步长码
如果newSampleCode&2:
差异+=步长码>>1
如果newSampleCode&1:
差异+=步长码>>2
差异+=步长码>>3
如果新闻示例代码为&8:
差异=-差异
预测样本+=差异
如果predictedSample>32767:
predictedSample=32767
如果predictedSample>3
如果原始样本&8:
差异=-差异
newSample+=差异
如果newSample>32767:
newSample=32767
elif newSample我可以看到一个问题:
elif indexcode>88:
indexcode=88
stepsizecode=stepsizeTable[indexcode]
应该是:
elif indexcode>88:
indexcode=88
stepsizecode=stepsizeTable[indexcode]
这是一个非常显著的区别
除此之外,我会尝试生成一个正弦测试音调,通过算法运行它并检查结果。我还试图排除字节和短字符之间转换的任何问题
此外,文档中还提供了一些测试向量,您可以使用这些向量逐步完成调试器。您可以发布您遇到的错误吗?杰夫,谢谢您的回复。我没有任何错误。脚本运行得很好,但音质很差。你有过这样的工作吗?需要同样的东西。是的,我需要。资料来源如下: