你能用python在循环中创建类吗?

你能用python在循环中创建类吗?,python,python-3.x,class,metaclass,Python,Python 3.x,Class,Metaclass,我有一种情况,我正在创建一组类,其中一组基本上是相同的,所以我想将它们做成一个循环。它们与注册系统一起使用,因此在使用方面没有任何问题,但我不确定如何使用一个决定类名的变量来定义一个类 简单的例子: classList = ['foo', 'bar', 'baz'] for className in classList: class {{{className}}}_calc(BaseCalc): def __init__ (self, dataFrame):

我有一种情况,我正在创建一组类,其中一组基本上是相同的,所以我想将它们做成一个循环。它们与注册系统一起使用,因此在使用方面没有任何问题,但我不确定如何使用一个决定类名的变量来定义一个类

简单的例子:

classList = ['foo', 'bar', 'baz']

for className in classList:
    class {{{className}}}_calc(BaseCalc): 
         def __init__ (self, dataFrame):
             self.column = dataFrame[className]
         def calc ():
             return self.column.sum()
显然,这是一个非常简单的情况。我无法将参数更改为init,因为已经存在一大堆参数,它们是更大结构的一部分

该示例的其余部分使用pandas语法,只是想了解如何使用它。。。但它实际上是与SQL数据库一起使用的,而且要复杂得多。。。我只是不想为“你为什么要这么做”辩护,我有充分的理由,就这样吧

类名在类行的{{}}中,表示它是一个变量,实际上在语法上并不正确。我想,问题是“我如何表示我使用{{{}}的目的?”

答案可能是元类,但我仍然不确定如何使我的类变量名

ETA:尝试使用@python\u用户回答:

classList = ['foooo', 'bar', 'baaz']

class Base ():
    def __init__ (self, buq):
        self.buq = buq

    def getBuq(self):
        return 'buq: ' + self.buq
    

for cls in classList:
    class TEMP(Base):
        className = cls
        def __init__ (self):
            self.qux = len(cls)
            Base.__init__(self, cls)

        def blee(self, inpt):
            return inpt+ self.qux
    TEMP.__name__ = f'{cls}'
    TEMP.__qualname__ = f'{cls}'
    globals()[cls] = TEMP
f = foo()

f.getBuq()

>>>> 'buq: baaz'

这只是给我一个巴兹班。三个人都在给巴兹。。。我做的事情真的很愚蠢吗?

但是,您可以使用type函数来创建这样的动态类。names=['name1','name2']假设您必须在python中创建10个类对象,并对它们执行一些操作,例如:obj_1=MyClass()other_object


希望我能帮到你。

好吧,有一种混乱的方法可以使用“exec()”函数来实现这一点,它接受任何字符串并执行它;然后可以将类构建为字符串并运行它。下面是一个构建类的示例,您可以通过查看最后打印的全局名称空间来声明它们

classList=['foo','bar','baz']
类BaseCalc():
定义初始化(自,数据帧):
self.column=dataFrame[className]
def calc():
返回self.column.sum()
对于类列表中的类名称:
模板=''类%s_计算(基本计算):
定义初始化(自,数据帧):
self.column=dataFrame[className]
def calc():
返回self.column.sum()“”“%className”
执行官(模板)
打印(globals())

您可以使用
globals()

然后可以执行
foo()
来创建类
foo
的对象。对于实际示例,您必须使用
\uuuu init\uuu
方法所需的参数进行调用。这只是为了证明它是有效的

print(type(foo()).__name__) # foo
print(type(bar()).__name__) # bar
print(type(baz()).__name__) # baz
如果您想更改类名,那么您可以这样做

Temp.__name__ = f'{className}_calc'
globals()[f'{className}_calc'] = Temp
正如wim在评论中指出的那样,您还需要设置
\uuuu qualname\uuu
<代码>温度.\uuuuuqalname\uuuuuu=f'{className}\u计算'

编辑:


由于类的方法中的名称查找是在运行时(而不是在编译时)执行的,因此代码段有一个bug
className
将始终引用
classList
中的最后一个元素(在本例中为
baz
),该名称不在循环的范围内,并且将是所有类的方法中
className
的值。(例如:
self.column=dataFrame[className]
)。使用type()创建一个具有动态指定名称的类,
type(f“MyClass{number}”,(),{})
。你必须在bases和dict中填充适当的内容我认为这可能会起作用,我目前正在尝试这样的方法:type(className+'calc',BaseCalc,{……}.但字典变得非常复杂,因为它有许多多行的lambda…可能是这里最简单的解决方案。你也应该设置
\uuuuuuqalname\uuuu
。谢谢,我想,:p@wimI喜欢这个答案的想法,但它不起作用。我会将我的代码添加到问题文本中…啊!我看到了你的最新编辑!好的,如果我将第一行替换为cls=cls,并在任何地方使用self.cls而不是cls,它都可以工作!谢谢!
Temp.__name__ = f'{className}_calc'
globals()[f'{className}_calc'] = Temp
class Temp:
    className = className # note this line
    def __init__ (self, dataFrame):
        self.column = dataFrame[self.className] # and this line with the original snippet