如何自行实现classmethod装饰器?剖析类方法核心功能
用自定义类实现等效
@classmethod的装饰器及类方法核心特性 类方法的核心可实现特性
- 绑定到类而非实例:调用时自动将类本身作为第一个参数传入,而非普通方法的实例对象
self - 支持双重调用方式:既可以通过
类名.方法名()调用,也可以通过实例对象.方法名()调用,两种方式都会传入类作为第一个参数 - 子类继承自动适配:子类调用继承的类方法时,传入的第一个参数是子类本身,而非父类
- 无法访问实例属性:由于参数是类而非实例,方法内部只能操作类级属性,无法直接访问实例专属属性
- 可作为工厂方法:常用于从不同格式输入生成类实例的场景
自定义类实现等效@classmethod装饰器
基于你提供的初始代码,我们利用Python的描述符协议(__get__方法)实现类方法的绑定逻辑,修正后的代码如下:
class classMethod: def __init__(self, func): # 保存被装饰的原函数 self.func = func def __get__(self, instance, cls=None): # 处理类调用和实例调用的场景 if cls is None: cls = type(instance) # 返回绑定了类的包装函数,自动传入类作为第一个参数 def bound_method(*args, **kwargs): return self.func(cls, *args, **kwargs) return bound_method
代码逻辑说明
__init__方法:接收被装饰的函数,将其保存为装饰器实例的属性,后续调用时直接复用原函数逻辑__get__方法:描述符协议的核心,当通过类或实例访问被装饰方法时触发:- 类调用场景(如
MyClass.method()):instance为None,cls直接传入当前类 - 实例调用场景(如
obj.method()):cls自动设为实例所属的类 - 返回的
bound_method会自动把类作为第一个参数传给原函数,完全模拟classmethod的核心行为
- 类调用场景(如
测试验证代码
class MyClass: # 使用自定义装饰器 @classMethod def print_class_info(cls, message): print(f"当前类:{cls.__name__},消息:{message}") # 类调用测试 MyClass.print_class_info("通过类调用") # 实例调用测试 obj = MyClass() obj.print_class_info("通过实例调用") # 子类继承测试 class MySubClass(MyClass): pass MySubClass.print_class_info("子类调用")
运行输出:
当前类:MyClass,消息:通过类调用 当前类:MyClass,消息:通过实例调用 当前类:MySubClass,消息:子类调用
内容的提问来源于stack exchange,提问作者hopeonthestreet18
相关产品推荐
相关产品推荐

