我在编写此程序时遇到问题。
我是python的新手。我使用的是python 2.7。(Anaconda)
以下是代码:
import numpy as numpy
import scipy
from scipy.io.wavfile import read
from scipy.io.wavfile import write
def getwavdata(file):
return scipy.io.wavfile.read(file)[1]
data=getwavdata('myvoice.wav')
print data
frameDuration = 0.01
frequency = 44100
numSamplesPerFrame = int(frequency * frameDuration)
frameSize=int(frequency*frameDuration)
signalEnergy=sum( [ abs(x)**2 for x in data ] )
print 'signal energy',signalEnergy
threshold=signalEnergy/3
print threshold
base=0
i=0
count=0
wordNumber=0
length=len(data)
print 'length of data is', length
word=[]
while i<length:
#print 'entered while loop'
frame=data[base:frameSize]
base=base+frameSize
frameEnergy=sum( [ abs(x)**2 for x in frame ] )
if frameEnergy < threshold:
count=count+1
word.append(frame)
word=numpy.array(word)
else :
count=0
word=[]
if count == 4:
print 'silence expected'
wordNumber=wordNumber+1
scipy.io.wavfile.write('word%d.wav' %wordNumber,44100,word)
count=0
word=[]
i = i+1
现在问题是当我第一次运行这个程序时,它打印了一些预期值。
它打印 signalEnergy =某些值约为3000000 且阈值=某些值约为1000000(1/3 of signalEnergy),但此处出现错误:
scipy.io.wavfile.write('word%d.wav' %wordNumber,44100,word)
错误:列表没有属性数组(类似的东西。不记得确切的句子)
我用Google搜索并发现write()将数组作为一个参数。
尝试修复该错误导致整个程序无效。
现在对于signalEnergy和阈值,我得到一个包含两个值的数组,而不是一个值。
我所做的改变:
while (base+frameSize)<length:
#print 'entered while loop'
frame=data[base:base+frameSize]
frameEnergy=sum( [ abs(x)**2 for x in frame ] )
print frameEnergy
if frameEnergy.all() < threshold.all():
count=count+1
word.append(frame)
else:
count=0
word=[]
if count == 4:
print 'word detected'
wordNumber=wordNumber+1
word = numpy.array(word)
scipy.io.wavfile.write('word'+str(wordNumber)+'.wav',44100,word)
count=0
word=[]
base = base + frameSize
Error:
[-29501 24682](**this is what it is giving as signalEnergy now**)
[-9834 8227]
length of data is 122240
Traceback (most recent call last):
File "C:\Users\Nancy Semwal\Documents\Python Scripts\program2.py", line 34, in <module>
if frameEnergy < threshold:
ValueError: The truth value of an array with more than one element is ambiguous. Use a.any() or a.all()
我理解错误,但我无法得到的是为什么它第一次正确运行?
可能是什么原因?我应该做出哪些改变?
答案 0 :(得分:0)
很难阅读您的代码并了解您所获得的确切错误,但我可以看到一些可能会让您感动的明显错误:
frame=data[base:frameSize]
一旦你完成循环frameSize时间,它将停止工作。既然你永远不会增加你的上限。切片基本上是:
myList[included_bottom_bound:excluded_top_bound]
frame=data[base:base+frameSize]
虽然我不能100%确定你的意图是什么。看起来你正在通过声音文件查看低音量的作品。第一次通过你每次前进一步并查看下一个数据块,而第二次通过你看一块,然后向前移动整个块大小的步骤。想象一下,声音文件看起来像这样:
*--*
其中*(星号)表示高音量, - (破折号)表示音量低。想象一下你的frameSize是2.一步一步(如在尝试1中)你有4个样本 if frameEnergy.all() < threshold.all():
frameEnergy是一个总和,所以它至少是一个int或long或者数字。你不能在这样的事情上做一个all()。同样处理门槛。
看看你的评论似乎signalEnergy现在不是一些简单的数字?这看起来很奇怪。也许您应该在代码中添加一些打印语句并找出原因。
我下载了一个示例wav文件,并针对它运行了代码,它工作并打印了一堆wordX.wav文件。他们并不介意你,但代码有效。我修复了空白问题等等......但这是我的最终代码:
<pre><code>import numpy as numpy
import scipy
from scipy.io.wavfile import read
from scipy.io.wavfile import write
def getwavdata(file):
return scipy.io.wavfile.read(file)[1]
data=getwavdata('E:\\Music\\Sounds\\carlin_letter.wav')
print data
frameDuration = 0.01
frequency = 44100
numSamplesPerFrame = int(frequency * frameDuration)
frameSize=int(frequency*frameDuration)
signalEnergy=sum( [ abs(x)**2 for x in data ] )
print 'signal energy',signalEnergy
threshold=signalEnergy/3
print threshold
base=0
i=0
count=0
wordNumber=0
length=len(data)
print 'length of data is', length
word=[]
while (base+frameSize)<length:
#print 'entered while loop'
frame=data[base:base+frameSize]
frameEnergy=sum( [ abs(x)**2 for x in frame ] )
print frameEnergy
if frameEnergy < threshold:
count=count+1
word.append(frame)
else:
count=0
word=[]
if count == 4:
print 'word detected'
wordNumber=wordNumber+1
word = numpy.array(word)
scipy.io.wavfile.write('e:\\music\\sounds\\word'+str(wordNumber)+'.wav',44100,word)
count=0
word=[]
base = base + frameSize
print "done"</code></pre>