如何在 class 中使用 'for loop' 定义列名 (IsDescription)

How to define column names using 'for loop' inside a class (IsDescription)

我们知道,如果我们需要使用pytables来定义一个table的列名,我们可以通过以下方式实现:

class Project(IsDescription):
    alpha = StringCol(20)
    beta  = StringCol(20) 
    gamma = StringCol(20)

其中 alpha、beta 和 gamma 是 table 所需的列名称。 但是假设我想使用一个包含列名的列表 "ColumnNames_list" ,如下所示: ColumnNames_list[0] = 阿尔法,ColumnNames_list[1] = 贝塔,ColumnNames_list[2] = 伽玛

那上面的class"Project"应该怎么定义呢?

我尝试了以下方法:

ColumnNames_list = []
ColumnNames_list[0] = alpha 
ColumnNames_list[1] = beta 
ColumnNames_list[2] = gamma

class Project(IsDescription):
    for i in range (0, 10):
        ColumnNames_list[i] = StringCol(20)  

显示错误:

TypeError:将不正确的值传递给 table 列。需要一个 Col(或 subclass)实例并得到:“2”。请使用 Col() 或后代构造函数来正确初始化列。

有几个选项。第一个(最简单的)是添加属性 after 你创建 class:

class Project(IsDescription):
    pass

for name in ColumnNames_List:
    setattr(Project, name, StringCol(20))

这个有很多不同的做法(例如,您可以通过 class 装饰器来完成)。

下一个选项是使用内置 type 构造 class:

names = {name: StringCol(20) for name in ColumnNames_List}
Project = type('Project', (IsDescription,), names)

这种方法的优点是它仍然有效,即使 IsDescription 上的某些时髦元 class 要求在 class 构造时间 上设置属性1。当我们谈论 metaclasses 时......你 可以 使用 metaclass 来做到这一点,但这几乎可以肯定是矫枉过正。

1这是一种罕见的情况,但一些流行的第 3 方库(例如 sqlalchemy)使用 metaclasses这样。