Python动态类创建
Python允许在运行时动态创建类、添加方法和属性,这是元编程的核心能力。
type 创建类
Python
# type(name, bases, dict)
MyClass = type('MyClass', (), {'attr': 123})
print(MyClass.__name__) # MyClass
print(MyClass.attr) # 123
obj = MyClass()
print(obj.attr) # 123
Python
# 带方法的类
def method(self):
return f"method called on {self}"
DynamicClass = type('DynamicClass', (), {
'value': 10,
'method': method
})
obj = DynamicClass()
print(obj.method()) # method called on <DynamicClass object>
Python
# 带继承的类
class Base:
base_attr = "from base"
def base_method(self):
return "base method"
Derived = type('Derived', (Base,), {
'derived_attr': "from derived"
})
d = Derived()
print(d.base_attr) # from base
print(d.base_method()) # base method
print(d.derived_attr) # from derived
动态添加方法
Python
class Base:
pass
# 添加实例方法
def greet(self, name):
return f"Hello, {name}!"
Base.greet = greet
obj = Base()
print(obj.greet("World")) # Hello, World!
# 添加类方法
import types
@classmethod
def class_method(cls):
return f"Class: {cls.__name__}"
Base.cm = class_method
print(Base.cm()) # Class: Base
# 添加静态方法
@staticmethod
def static_method():
return "static"
Base.sm = static_method
print(Base.sm()) # static
Python
# 动态绑定实例方法
class Container:
pass
def operation(self, x):
return self.value * x
obj = Container()
obj.value = 10
# 方法绑定到单个实例
obj.operation = types.MethodType(operation, obj)
print(obj.operation(5)) # 50
# 另一个实例没有这个方法
obj2 = Container()
# obj2.operation # AttributeError
动态添加属性
Python
class Dynamic:
pass
obj = Dynamic()
# 直接添加
obj.attr1 = "value1"
setattr(obj, 'attr2', "value2")
# 通过 __dict__ 批量添加
obj.__dict__.update({
'attr3': "value3",
'attr4': "value4"
})
print(obj.attr1, obj.attr2, obj.attr3) # value1 value2 value3
# 类级别添加
Dynamic.class_attr = "class value"
print(Dynamic().class_attr) # class value
工厂模式生成类
Python
def create_model_class(name, fields):
"动态创建数据模型类"
# __init__ 方法
def __init__(self, **kwargs):
for field in fields:
setattr(self, field, kwargs.get(field))
# __repr__ 方法
def __repr__(self):
values = ', '.join(
f"{f}={getattr(self, f, None)}"
for f in fields
)
return f"{name}({values})"
# 类属性
attrs = {
'__init__': __init__,
'__repr__': __repr__,
'_fields': fields,
}
# 创建类
return type(name, (), attrs)
# 使用工厂
User = create_model_class('User', ['id', 'name', 'email'])
Product = create_model_class('Product', ['id', 'title', 'price'])
u = User(id=1, name="Alice", email="alice@example.com")
print(u) # User(id=1, name=Alice, email=alice@example.com)
p = Product(id=10, title="Book", price=29.9)
print(p) # Product(id=10, title=Book, price=29.9)
Python
# 泛型类工厂
def create_container_class(item_type):
"创建特定类型的容器类"
def __init__(self, items=None):
self._items = []
if items:
for item in items:
self.add(item)
def add(self, item):
if not isinstance(item, item_type):
raise TypeError(f"Expected {item_type.__name__}")
self._items.append(item)
def __iter__(self):
return iter(self._items)
def __len__(self):
return len(self._items)
name = f"{item_type.__name__}Container"
return type(name, (), {
'__init__': __init__,
'add': add,
'__iter__': __iter__,
'__len__': __len__,
'_item_type': item_type,
})
IntContainer = create_container_class(int)
StrContainer = create_container_class(str)
ic = IntContainer([1, 2, 3])
print(list(ic)) # [1, 2, 3]
# ic.add("string") # TypeError
动态继承组合
Python
def create_mixin_class(*bases):
"组合多个基类"
class_name = "Mixed" + "".join(b.__name__ for b in bases)
return type(class_name, bases, {
'combined_attrs': lambda self: [
getattr(self, attr)
for base in bases
for attr in base.__dict__
if not attr.startswith('_')
]
})
class A:
a_attr = "a"
class B:
b_attr = "b"
MixedAB = create_mixin_class(A, B)
obj = MixedAB()
print(obj.a_attr) # a
print(obj.b_attr) # b
动态属性描述符
Python
def create_property(name, default=None, validator=None):
"动态创建属性描述符"
storage_name = f'_internal_{name}'
def getter(self):
return getattr(self, storage_name, default)
def setter(self, value):
if validator and not validator(value):
raise ValueError(f"Invalid value for {name}")
setattr(self, storage_name, value)
return property(getter, setter)
def create_validated_class(name, schema):
"根据 schema 创建带验证的类"
attrs = {}
for field, spec in schema.items():
attrs[field] = create_property(
field,
default=spec.get('default'),
validator=spec.get('validator')
)
return type(name, (), attrs)
# 定义 schema
schema = {
'name': {'default': '', 'validator': lambda x: isinstance(x, str)},
'age': {'default': 0, 'validator': lambda x: isinstance(x, int) and x >= 0},
}
Person = create_validated_class('Person', schema)
p = Person()
p.name = "Alice"
p.age = 30
print(p.name, p.age) # Alice 30
# p.age = -1 # ValueError
类型注册系统
Python
class TypeRegistry:
"动态类型注册与创建"
_types = {}
@classmethod
def register(cls, name, definition):
"注册类型定义"
cls._types[name] = definition
@classmethod
def create(cls, name, **kwargs):
"创建指定类型的实例"
if name not in cls._types:
raise KeyError(f"Unknown type: {name}")
definition = cls._types[name]
type_class = cls._create_class(name, definition)
return type_class(**kwargs)
@classmethod
def _create_class(cls, name, definition):
"根据定义创建类"
if hasattr(definition, '__call__'):
# 定义是函数或类
return definition
# 定义是字典
return type(name, (), definition)
# 注册类型
TypeRegistry.register('simple', {'value': 0})
TypeRegistry.register('complex', lambda: type('Complex', (), {'data': []}))
obj = TypeRegistry.create('simple')
print(obj.value) # 0
动态方法生成
Python
def create_accessor_methods(fields):
"为字段生成 getter/setter"
methods = {}
for field in fields:
# getter
def getter(self, f=field):
return getattr(self, f'_data', {}).get(f)
# setter
def setter(self, value, f=field):
data = getattr(self, '_data', {})
data[f] = value
setattr(self, '_data', data)
methods[f'get_{field}'] = getter
methods[f'set_{field}'] = setter
return methods
def create_data_class(name, fields):
"创建带 accessor 的数据类"
methods = create_accessor_methods(fields)
methods['_data'] = {}
def __init__(self, **kwargs):
self._data = kwargs
methods['__init__'] = __init__
return type(name, (), methods)
Data = create_data_class('Data', ['x', 'y', 'z'])
d = Data(x=1, y=2, z=3)
print(d.get_x()) # 1
d.set_x(10)
print(d.get_x()) # 10
要点总结
- **
type(name, bases, dict)**是动态创建类的核心 - **
types.MethodType(func, obj)**绑定方法到实例 - 类方法和静态方法可直接赋值到类
- 工厂模式可根据配置动态生成类
- 动态类创建适用于ORM、数据模型、插件系统等场景
📝 发现内容有误?点击此处直接编辑