0

在我的程序中,我需要类(可以是某个线程)来检查诸如“say_list”之类的列表,当其他类向其中添加一些文本时,pyttsx 会说出该文本。我在 pyttsx文档中搜索并找到了一些外部循环功能,但我找不到可以正常工作的示例。我想要这样的东西:

import pyttsx
import threading

class VoiceAssistant(threading.Thread):
    def __init__(self):
        super(VoiceAssistant, self).__init__()
        self.engine = pyttsx.init()
        self.say_list = []

    def add_say(self, msg):
        self.say_list.append(msg)

    def run(self):
        while True:
            if len(self.say_list) > 0:
                self.engine.say(self.say_list[0])
                self.say_list.remove(self.say_list[0])


if __name__ == '__main__':
    va = VoiceAssistant()
    va.start()

谢谢。

4

1 回答 1

2

我可以通过使用 python 内置的 Queue 类获得正确的结果:

import pyttsx
from Queue import Queue
from threading import Thread

q = Queue()

def say_loop():
    engine = pyttsx.init()
    while True:
        engine.say(q.get())
        engine.runAndWait()
        q.task_done()

def another_method():
    t = Thread(target=say_loop)
    t.daemon = True
    t.start()
    for i in range(0, 3):
        q.put('Sally sells seashells by the seashore.')
    print "end of another method..."

def third_method():
    q.put('Something Something Something')

if __name__=="__main__":
    another_method()
    third_method()
    q.join() # ends the loop when queue is empty

上面是我整理的一个简单的例子。它使用“队列/消费者”模型来允许单独的函数/类访问同一个队列,然后是一个在队列有项目时将执行的工作人员。应该很容易适应您的需求。

关于队列的进一步阅读:https ://docs.python.org/2/library/queue.html 在您链接到的文档中似乎有一个接口,但似乎您已经在单独的线程轨道上,所以这似乎更接近你想要的。

这是您的代码的修改版本:

import pyttsx
from Queue import Queue
import threading

class VoiceAssistant(threading.Thread):
    def __init__(self):
        super(VoiceAssistant, self).__init__()
        self.engine = pyttsx.init()
        self.q = Queue()
        self.daemon = True

    def add_say(self, msg):
        self.q.put(msg)

    def run(self):
        while True:
            self.engine.say(self.q.get())
            self.engine.runAndWait()
            self.q.task_done()


if __name__ == '__main__':
    va = VoiceAssistant()
    va.start()
    for i in range(0, 3):
        va.add_say('Sally sells seashells by the seashore.')
    print "now we want to exit..."
    va.q.join() # ends the loop when queue is empty
于 2016-08-21T22:05:23.770 回答