Python不允许我在类定义尚未完成时使用类内部的方法

2024-06-28 19:22:56 发布

您现在位置:Python中文网/ 问答频道 /正文

我使用python2.6作为批处理脚本替换。它将通过双击启动,因此所有到stdout的输出都将被用户丢失/忽略。所以,我决定添加日志,为了简单起见,我为此编写了一个类。我的想法是我可以在我的代码中的任何地方使用Logging.Logger,这样记录器就可以运行了。在

我希望一个目录中的旧日志文件不超过10个,所以我手动清除旧的日志文件。我还没有通过API找到这样的功能,而且我偏执,想要记录所有的东西,万一有文件在日志目录中有意外的名称。在

所以,下面是我在这个类上的尝试,但是当我尝试测试(运行)它时,我得到了一个错误:

>>> ================================ RESTART ================================
>>> 

Traceback (most recent call last):
  File "C:/AutomationScripts/build scripts/Deleteme.py", line 6, in <module>
    class Logging:
  File "C:/AutomationScripts/build scripts/Deleteme.py", line 42, in Logging
    __clearOldLogs(dummySetting)
  File "C:/AutomationScripts/build scripts/Deleteme.py", line 38, in __clearOldLogs
    _assert(Logger, 'Logger does not exist yet! Why?')
NameError: global name '_assert' is not defined
>>> 

是的,我来自Java/C的背景。我可能不是在用“Python”的方式做事。请帮助我做正确的事情,并请给出一个完整的答案,这将是可行的,而不是简单地指出我的知识漏洞。我相信我已经提供了足够的代码示例。抱歉,如果没有设置类,它将无法运行,但希望您能理解这一点。在

^{pr2}$

欢迎提出相关问题、风格建议和完整答案。谢谢!在


Tags: 文件代码inpybuild目录loggingline
3条回答

一些评论。在

  1. 不要使用双下划线,除非你绝对确定你必须这么做,并说明原因。

  2. 要访问\u assert方法,请使用self调用它。如是:self.\u assert(Logger,'Logger不存在!为什么?')在静态方法中,如您的示例所示,使用类名Logger.\u assert()。Python非常明确。

  3. 类只在类定义的末尾创建。Python就是这样。但你的错误与此无关。

  4. 我不知道这个代码应该做什么:

    # Settings is a separate class (not dependent on this one).    
    Logger = __createLogger(Settings.LOGGING)
    __clearOldLogs(Settings.LOGGING)
    

    但我想你应该把它放在__init__方法中。在类构造期间,我没有立即看到任何需要访问类的代码。

  5. __createLogger是一个奇怪的函数。这个类不叫Logger吗?这不应该是Logger类的__init__

更换管路

_assert(Logger, 'Logger does not exist yet! Why?')

^{pr2}$

这是因为您将_assert定义为类的静态方法,而静态方法必须被称为ClassName.methodName,即使您是从此类实例的方法中调用它。在

您得到了这个异常,因为您调用的是_assert(),而不是{}。错误消息告诉您它在模块的全局命名空间中而不是在类命名空间中查找_assert();要使它在后者中查找,必须显式地指定它。在

当然,在本例中,您尝试在类仍在定义时执行此操作,并且在类完成之前名称是不可用的,因此很难做到这一点。在

一种解决方案是取消以下两行的缩进(我编辑了这两行以使用完全限定名),这样它们就在类定义之外;它们将在类定义之后立即执行。在

Logger = Logging.__createLogger(Settings.LOGGING)
Logging.__clearOldLogs(Settings.LOGGING)

一个有帮助的风格建议:与其用一堆静态方法组成一个类,不如考虑让它们成为模块中的顶级函数。你的模块用户(包括你自己)会发现更容易获得他们想要的功能。没有理由仅仅将类用作容器;模块本身就已经是这样一个容器了。在

一个模块基本上是一个*.py文件(虽然您可以创建具有多个文件的模块,但现在就可以了)。当您执行import操作时,您要导入的是一个模块。在您的示例中,tkMessageBox和{}都是模块。所以只需创建一个单独的文件(确保其名称与现有的Python模块名不冲突),将其保存在与主脚本相同的目录中,然后将其导入主脚本。如果您将其命名为mylogging.py,那么您将import mylogging并以mylogging.clearOldLogs()或其他方式访问其中的函数(类似于现在将它们作为类来处理)。在

Python中的“Global”名称并不是真正的全局名称,它们只是定义在其中的模块的全局名称。所以模块是划分功能的一个好方法,尤其是那些您希望在将来的脚本中重用的部分(如日志记录)。在

相关问题 更多 >