【问题标题】:Can you somehow use a local function on a global level in python?你能以某种方式在 python 的全局级别上使用本地函数吗?
【发布时间】:2020-12-31 18:06:10
【问题描述】:

我正在编写一个程序,我正在使用espeak 库让它说话。问题是我已经编写了我的程序,但现在我想在开始时询问用户他是希望程序与他交谈还是仅仅依靠阅读。因此,如果他说是,则程序使用espeak 说话,但如果他说否,则程序不使用espeak,所以我被困在no 部分。

我想问一个问题并根据答案使用正确的函数,但问题是它是一个本地函数,所以当你使用函数 espeak() 时它会说

NameError: name 'espeak' is not defined 

这就是我想要的:

import os
ai_talk = False
# MAKE THE AI SPEAK, OR NOT
def speak_or_not():
    global ai_talk
    
    speak_or_n = input("Do you want me to speak or not?\nPS: input Y/N\n").casefold()
    while not ai_talk:
        if (speak_or_n == "y") or (speak_or_n == "yes"):
            def espeak(text):
                command = 'espeak -v +f2 -p25 '+'"'+text+'"'
                os.system(command)
                return
            ai_talk = True

        elif (speak_or_n == "n") or (speak_or_n == "no"):
            def espeak(text):
                return
            ai_talk = True

        else:
            speak_or_n = input("You can only input Y/N").casefold()
    return

speak_or_not()

print("Hello there! how are you doing?")
espeak("Hello there! how are you doing?")

那么有没有办法让def espeak() 函数在全局级别上工作,以便我可以在程序的其余部分使用它?

(除了应对洞的东西并将其粘贴在没有espeak功能的no部分)

【问题讨论】:

    标签: python function espeak local-functions global-functions


    【解决方案1】:

    如果你只是return espeak,你可以在主程序中保存你想要的定义。这就是 Python 装饰器的工作方式。这是一个简单的例子:

    def fpick(flag):
        if flag:
            def display():
                print('flag was set')
        else:
            def display():
                print('flag was off')
    
        return display
    
    display = fpick(True)
    display()
    
    display = fpick(False)
    display()
    

    输出:

    flag was set
    flag was off
    
     was set
    flag
    

    关闭

    【讨论】:

      【解决方案2】:

      下面是如何编写它,使speak_or_not 返回espeak 函数。我添加了类型注释,以便更容易查看内部函数如何与外部函数交互——speak_or_not 函数返回一个 Callable[[str], None](一个接受 str 参数并返回 None 的函数),并且espeak 的两个版本都匹配此类型。

      import os
      from typing import Callable
      
      def speak_or_not() -> Callable[[str], None]:
          """Return a function that either makes the AI speak or is a no-op."""
          speak_or_n = input("Do you want me to speak or not?\nPS: input Y/N\n").casefold()
          while True:
              if speak_or_n in ("y", "yes"):
                  def espeak(text: str) -> None:
                      os.system(f'espeak -v +f2 -p25 "{text}"')
                  return espeak
              if speak_or_n in ("n", "no"):
                  def espeak(text: str) -> None:
                      return
                  return espeak
              speak_or_n = input("You can only input Y/N").casefold()
      
      espeak = speak_or_not()
      
      print("Hello there! how are you doing?")
      espeak("Hello there! how are you doing?")
      

      请注意,global ai_talk 不是必需的,因为该值从未在函数外部使用,实际上在函数内部它仅用于中断循环,如果您在终止条件后return,则这是不必要的满足,所以即使在函数内也根本不需要这个值。

      【讨论】:

      • nitpick: in 检查最多 30 个元素的元组更快。因此,通过使用 .. in ('yes', 'y')` 而不是 set,您可以节省几纳秒的机器时间
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-11-23
      • 1970-01-01
      • 2023-02-14
      • 2021-04-06
      • 2022-11-29
      • 1970-01-01
      • 2016-12-13
      相关资源
      最近更新 更多