【问题标题】:How can i pause a thread until another thread has stopped its action in python?我如何暂停一个线程,直到另一个线程停止它在 python 中的操作?
【发布时间】:2019-12-27 23:28:30
【问题描述】:

我有两个线程同时运行,speechRecognitionspeakBack。这两个线程都在 while 循环 (while True: #do something) 中运行。 语音识别一直在等待麦克风输入。然后,一旦收到,它将口头输入的文本版本保存到一个文件中,该文件由我的第二个线程 speakBack 加载,并通过扬声器说话。 我的问题是,当通过扬声器说出短语时,它被麦克风拾取然后翻译并再次保存到该文件中进行处理,从而导致无限循环。

如何让speechRecognition 线程自行挂起,等待speakBack 线程停止通过扬声器输出声音,然后继续收听下一个语音输入? 我分别使用 SpeechRecognition 库和 pyttsx3 库进行语音识别和语音输出。

【问题讨论】:

    标签: python-3.x multithreading speech-recognition pyttsx


    【解决方案1】:

    做到这一点的方法是在线程之间共享状态(或者使用线程可以存储和读取以指示其进度的全局变量,或者使用传递给每个线程的可变引用)。我将在下面给出的解决方案涉及一个存储可变引用的全局变量,但您可以轻松地将队列传递给两个线程,而不是全局存储。

    使用队列是在 python 中的线程之间传递消息的一种非常标准的方式,因为队列已经以线程安全的方式编写,因此您不必考虑同步和锁定。此外,对queue.get 的阻塞调用是以不涉及在while 循环中重复和浪费地检查条件变量的方式实现的。

    下面是一些代码的样子:

    import queue
    
    START_SPEAK_BACK = 0
    START_SPEECH_RECOGNITION = 1
    messageQueue = queue.Queue()
    
    # thread 1
    def speechRecognition():
      while True:
        # wait for input like you were doing before
        # write to file as before
        # put message on the queue for other thread to get
        messageQueue.put(START_SPEAK_BACK)
        # Calling `get` with no arguments makes the call be
        # "blocking" in the sense that it won't return until
        # there is an element on the queue to get.
        messageFromOtherThread = messageQueue.get()
        # logically, messageFromOtherThread can only ever be
        # START_SPEECH_RECOGNITION, but you could still
        # check that this is true and raise an exception if not.
    
    # thread 2
    def speakBack():
      while True:
        messageFromOtherThread = messageQueue.get()
        # likewise, this message will only be START_SPEAK_BACK
        # but you could still check.
        # Here, fill in the code that speaks through the speakers.
        # When that's done:
        messageQueue.put(START_SPEECH_RECOGNITION)
    

    一些cmets:

    1. 此解决方案使用单个队列。它可以很容易地使用两个队列,一个用于 speakBack —> SpeechRecognition 通信,另一个用于 SpeechRecognition —> 通信。如果两个线程同时生成消息,这可能更有意义。

    2. 此解决方案实际上并不涉及检查消息的内容。但是,如果您需要在线程之间传递其他信息,您可以非常轻松地将对象或数据作为消息传递(而不仅仅是常量值)

    3. 最后,我不清楚你为什么不在同一个线程中运行所有代码。看起来你希望你的程序遵循一系列非常清晰的(串行)步骤:获取音频输入,将其写入文件,回复它,重新开始。将所有内容编写为普通的、串行的、无线程的 Python 程序可能更有意义。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-09-29
      • 1970-01-01
      相关资源
      最近更新 更多