前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >python 元类做类型检查

python 元类做类型检查

作者头像
用户5760343
发布2019-12-12 18:00:14
5960
发布2019-12-12 18:00:14
举报
文章被收录于专栏:sktjsktj

作为一个具体的应用例子,下面定义了一个元类,它会拒绝任何有混合大小写名字作为方法的类定义

class NoMixedCaseMeta(type): def new(cls, clsname, bases, clsdict): for name in clsdict: if name.lower() != name: raise TypeError('Bad attribute name: ' + name) return super().new(cls, clsname, bases, clsdict)

class Root(metaclass=NoMixedCaseMeta): pass

class A(Root): def foo_bar(self): # Ok pass

class B(Root): def fooBar(self): # TypeError pass

检查元类的签名

from inspect import signature import logging

class MatchSignaturesMeta(type):

def __init__(self, clsname, bases, clsdict):
    super().__init__(clsname, bases, clsdict)
    sup = super(self, self)
    for name, value in clsdict.items():
        if name.startswith('_') or not callable(value):
            continue
        # Get the previous definition (if any) and compare the signatures
        prev_dfn = getattr(sup,name,None)
        if prev_dfn:
            prev_sig = signature(prev_dfn)
            val_sig = signature(value)
            if prev_sig != val_sig:
                logging.warning('Signature mismatch in %s. %s != %s',
                                value.__qualname__, prev_sig, val_sig)

Example

class Root(metaclass=MatchSignaturesMeta): pass

class A(Root): def foo(self, x, y): pass

def spam(self, x, *, z):
    pass

Class with redefined methods, but slightly different signatures

class B(A): def foo(self, a, b): pass

def spam(self,x,z):
    pass

在元类中选择重新定义 new() 方法还是 init() 方法取决于你想怎样使用结果类。 new() 方法在类创建之前被调用,通常用于通过某种方式(比如通过改变类字典的内容)修改类的定义。 而 init() 方法是在类被创建之后被调用,当你需要完整构建类对象的时候会很有用。 在最后一个例子中,这是必要的,因为它使用了 super() 函数来搜索之前的定义。 它只能在类的实例被创建之后,并且相应的方法解析顺序也已经被设置好了。

最后一个例子还演示了Python的函数签名对象的使用。 实际上,元类将每个可调用定义放在一个类中,搜索前一个定义(如果有的话), 然后通过使用 inspect.signature() 来简单的比较它们的调用签名。

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 作为一个具体的应用例子,下面定义了一个元类,它会拒绝任何有混合大小写名字作为方法的类定义
  • 检查元类的签名
  • Example
  • Class with redefined methods, but slightly different signatures
相关产品与服务
日志服务
日志服务(Cloud Log Service,CLS)是腾讯云提供的一站式日志服务平台,提供了从日志采集、日志存储到日志检索,图表分析、监控告警、日志投递等多项服务,协助用户通过日志来解决业务运维、服务监控、日志审计等场景问题。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档