Python 3.9 使用静态方法初始化类的常量会产生错误

问题描述

我正在尝试在 python3.9 中创建一个类,通过从静态方法加载文件来动态加载类的常量值,如下所示:

class sqlQueries(object):

    CLIPAPP = sqlQueries.load_query_statement('clinapp.sql')

    MENSALIDADES = sqlQueries.load_query_statement('mensalidades.sql')

    SINISTRO = sqlQueries.load_query_statement('sinistro.sql')


    @staticmethod
    def load_query_statement(sql_file,format_params=None):
        curr_dir = os.getcwd()
        sql_dir = os.path.join(curr_dir,'queries',sql_file)
        with open(sql_dir,'r') as sql:
            query = sql.read()
            query = query.format(format_params)
        return query

但是这样做时,会产生以下错误

---------------------------------------------------------------------------
NameError                                 Traceback (most recent call last)
<ipython-input-49-ddf4f8beb954> in <module>
----> 1 class sqlQueries(object):
      2 
      3     CLIPAPP = sqlQueries.load_query_statement('clinapp.sql')
      4 
      5     MENSALIDADES = sqlQueries.load_query_statement('mensalidades.sql')

<ipython-input-49-ddf4f8beb954> in sqlQueries()
      1 class sqlQueries(object):
      2 
----> 3     CLIPAPP = sqlQueries.load_query_statement('clinapp.sql')
      4 
      5     MENSALIDADES = sqlQueries.load_query_statement('mensalidades.sql')

NameError: name 'sqlQueries' is not defined

我该如何解决

解决方法

我该如何解决?

不这样做。

首先,您从三个方面误解了 Python 的执行模型

  • 撇开控制流不谈,Python 代码从上到下线性执行
  • 类语句的“主体”是执行代码,围绕执行环境(范围)有一些魔法,但仅此而已
  • 在类主体完全执行之前不会创建类对象

本质上,

class Foo:
    ...

是语法糖:

def Foo_body():
    ...
    return locals()
Foo = type('Foo',(object,),Foo_body())

从这里你可以看到两件事:

  • 类体语句不可能引用类体中跟随它的东西
  • “方法”只不过是一个沼泽标准的常规函数​​,直到主体完全执行完毕

其次,静态方法在 Python 中很少有用,正如大约 20 年前的旧 Python is not Java 文章指出的那样:

Java 中的静态方法不会转换为 Python 类方法。 [...] Java 静态方法的惯用翻译通常是模块级函数,而不是类方法或静态方法。

所以

  • 如果您正在编写静态方法,则不应
  • 如果你正在编写一个类方法,你应该认真考虑它是否真的需要,例如您可能需要覆盖非默认构造函数(这本质上是用例)

否则……就写个函数吧。功能很酷。这里你应该只写一个函数,没有理由写一个静态方法。

坦率地说,我不确定这个类本身是否有用。