位置: 编程技术 - 正文

Python 描述符(Descriptor)入门(python 描述符类)

编辑:rootadmin

推荐整理分享Python 描述符(Descriptor)入门(python 描述符类),希望有所帮助,仅作参考,欢迎阅读内容。

文章相关热门搜索词:python字符串描述,描述符的格式,python描述符详解,python 描述符协议,python描述符详解,python 描述符 属性,python描述符详解,python 描述符 属性,内容如对您有帮助,希望把文章链接给更多的朋友!

很久都没写 Flask 代码相关了,想想也真是惭愧,然并卵,这次还是不写 Flask 相关,不服你来打我啊(就这么贱,有本事咬我啊

这次我来写一下 Python 一个很重要的东西,即 Descriptor (描述符)

初识描述符

老规矩, Talk is cheap,Show me the code. 我们先来看看一段代码

这段代大家肯定很熟悉,恩, property 嘛,谁不知道呢,但是 property 的实现机制大家清楚么?什么不清楚?那还学个毛的 Python 啊。。。开个玩笑,我们看下面一段代码

看起来是不是很复杂,没事,我们来一步步的看。不过这里我们首先给出一个结论: Descriptors 是一种特殊 的对象,这种对象实现了 __get__ , __set__ , __delete__ 这三个特殊方法。

详解描述符

说说 Property

在上文,我们给出了 Propery 实现代码,现在让我们来详细说说这个

首先,如果你对装饰器不了解的话,你可能要去看看这篇文章,简而言之,在我们正式运行代码之前,我们的解释器就会对我们的代码进行一次扫描,对涉及装饰器的部分进行替换。类装饰器同理。在上文中,这段代码

会触发这样一个过程,即 full_name=Property(full_name) 。然后在我们后面所实例化对象之后我们调用 person.full_name 这样一个过程其实等价于 person.full_name.__get__(person) 然后进而触发 __get__() 方法里所写的 return self.fget(obj) 即原本上我们所编写的 def full_name 内的执行代码。

这个时候,同志们可以去思考下 getter() , setter() ,以及 deleter() 的具体运行机制了=。=如果还是有问题,欢迎在评论里进行讨论。

Python 描述符(Descriptor)入门(python 描述符类)

关于描述符

还记得之前我们所提到的一个定义么: Descriptors 是一种特殊的对象,这种对象实现了 __get__ , __set__ , __delete__ 这三个特殊方法 。然后在 Python 官方文档的说明中,为了体现描述符的重要性,有这样一段话:“They are the mechanism behind properties, methods, static methods, class methods, and super(). They are used throughout Python itself to implement the new style classes introduced in version 2.2. ” 简而言之就是 先有描述符后有天,秒天秒地秒空气 。恩,在新式类中,属性,方法调用,静态方法,类方法等都是基于描述符的特定使用。

OK,你可能想问,为什么描述符是这么重要呢?别急,我们接着看

使用描述符

首先请看下一段代码

classA(object):#注:在 Python 3.x 版本中,对于 new class 的使用不需要显式的指定从 object 类进行继承,如果在 Python 2.X(x>2)的版本中则需要

大家都注意到了我们存在着这样一个语句 a.a() ,好的,现在请大家思考下,我们在调用这个方法的时候发生了什么?

OK?想出来了么?没有?好的我们继续

首先我们调用一个属性的时候,不管是成员还是方法,我们都会触发这样一个方法用于调用属性 __getattribute__() ,在我们的 __getattribute__() 方法中,如果我们尝试调用的属性实现了我们的描述符协议,那么会产生这样一个调用过程 type(a).__dict__['a'].__get__(b,type(b)) 。好的这里我们又要给出一个结论了:“在这样一个调用过程中,有这样一个优先级顺序,如果我们所尝试调用属性是一个 data descriptors ,那么不管这个属性是否存在我们的实例的 __dict__ 字典中,优先调用我们描述符里的 __get__ 方法,如果我们所尝试调用属性是一个 non data descriptors ,那么我们优先调用我们实例里的 __dict__ 里的存在的属性,如果不存在,则依照相应原则往上查找我们类,父类中的 __dict__ 中所包含的属性,一旦属性存在,则调用 __get__ 方法,如果不存在则调用 __getattr__() 方法”。理解起来有点抽象?没事,我们马上会讲,不过在这里,我们先要解释下 data descriptors 与 non data descriptors ,再来看一个例子。什么是 data descriptors 与 non data descriptors 呢?其实很简单,在描述符中同时实现了 __get__ 与 __set__ 协议的描述符是 data descriptors ,如果只实现了 __get__ 协议的则是 non data descriptors 。好了我们现在来看个例子:

好的,让我们仔细来看看这段代码,首先类描述符 @lazyproperty 的替换过程,前面已经说了,我们不在重复。接着,在我们第一次调用 c.area 的时候,我们首先查询实例 c 的 __dict__ 中是否存在着 area 描述符,然后发现在 c 中既不存在描述符,也不存在这样一个属性,接着我们向上查询 Circle 中的 __dict__ ,然后查找到名为 area 的属性,同时这是一个 non data descriptors ,由于我们的实例字典内并不存在 area 属性,那么我们便调用类字典中的 area 的 __get__ 方法,并在 __get__ 方法中通过调用 setattr 方法为实例字典注册属性 area 。紧接着,我们在后续调用 c.area 的时候,我们能在实例字典中找到 area 属性的存在,且类字典中的 area 是一个 non data descriptors ,于是我们不会触发代码里所实现的 __get__ 方法,而是直接从实例的字典中直接获取属性值。

描述符的使用

描述符的使用面很广,不过其主要的目的在于让我们的调用过程变得可控。因此我们在一些需要对我们调用过程实行精细控制的时候,使用描述符,比如我们之前提到的这个例子

利用描述符的特性实现懒加载,再比如,我们可以控制属性赋值的值

如上面的例子所描述的一样,我们可以判断所传入的值是否有效等等。

Flask框架的学习指南之开发环境搭建 Flask是一个使用Python编写的轻量级Web应用框架。其WSGI工具箱采用Werkzeug,模板引擎则使用Jinja2。很多功能的实现都参考了django框架。由于项目需要,在此

Flask框架的学习指南之制作简单blog系统 之前写了一篇flask开发环境搭建,今天继续,进行一个实战小项目-blog系统。blog系统很简单,只有一个页面,然后麻雀虽小五脏俱全。这里目的不是为了

Flask框架的学习指南之用户登录管理 继续flask的学习之旅。今天介绍flask的登陆管理模块,还记得上一篇中的blog小项目么,登录是咱们自己写的验证代码,大概有以下几个步骤:1、在登录

标签: python 描述符类

本文链接地址:https://www.jiuchutong.com/biancheng/383488.html 转载请保留说明!

上一篇:独特的python循环语句(python中循环)

下一篇:Flask框架的学习指南之开发环境搭建(flask框架官方文档)

  • 报废的原材料
  • 合伙企业如何纳入合并报表
  • 不予认定一般纳税人
  • 个人注册公司有什么优惠政策
  • 工程机械租赁税点
  • 增值税小规模纳税人优惠政策
  • 公司分红是按股权比例分配吗
  • 联营企业和合营企业长期股权投资的方式
  • 电子发票丢失如何税前扣除
  • 空白作废什么意思
  • 个人境外存款利息收入收税
  • 装卸费和保险费是价外费用吗
  • 海关免税设备清单
  • 法人转钱进公账要交税吗
  • 库存商品盘盈盘亏表
  • 出口退税总是差进项票怎么处理
  • 劳务税能不能抵扣
  • 粮食仓储设施设备管理
  • 发票章和税号不匹配
  • 企业未代扣代缴个税
  • 上年的费用本年能报销吗
  • 怎么知道一个公众号有多少人关注
  • 增值税小规模纳税人免征增值税政策
  • 汇缴交的所得税如何做账
  • 红冲无票收入怎么报税
  • 保安费用分录
  • 如何激活windows11专业版?
  • 费用报销单正确填写格式
  • 外购货物用于建造厂房可以抵扣进项税吗
  • 转账和电汇哪个便宜
  • php调用外部接口
  • ajax调用php函数
  • 无法启用网络发展
  • Radio.exe - Radio是什么进程 有什么用
  • 支付宝花呗服务费收费标准
  • 应收债权换入无偿收益
  • 罚款收入营业外收入还是其他应收款
  • 手续费及佣金扣除标准
  • 企业如何减少税收
  • 逾期包装物押金收入计入什么科目
  • 事业单位会计专业知识考什么
  • 弥补以前年度亏损后缴纳所得税
  • react最新教程
  • webpack插件执行顺序
  • 存货盘盈盘亏会涉及到其他应收款吗
  • 小规模纳税人出租不动产税率是5%还是3%
  • 企业所得税退税如何进行账务处理
  • 合同 成本
  • mybatis调用存储过程详解
  • nosql sql
  • bkuzmic/jquerycrossdomaindataplugin
  • 进项税计税依据
  • 营业收入是指从全部营业收入中扣除
  • 核电站弃置费用通常多少钱
  • 实收资本账务处理流程
  • 先征后退增值税是否征收企业所得税
  • 报销差旅费大于预借差旅费会计分录
  • 在异地施工就要在异地交税吗
  • 租赁房屋取得发票怎么开
  • 企业给加盟店的钱怎么算
  • 机票行程单如何看座位等级
  • 非贸付汇计税基础
  • 经营租入的固定资产计入什么科目
  • 差旅费借记什么科目
  • 农业技术人员是什么意思
  • 每月分红会计分录
  • 会计交接事项有哪些
  • mysql5.5安装配置教程
  • debian系统教程
  • win10怎么关闭右下角图标
  • centos7.9关机
  • SPBBCSvc.exe - SPBBCSvc进程是什么文件 有什么作用
  • win7电脑桌面图标不见了右键也没用
  • win8切换到桌面
  • linux常用命令详解
  • 详解中国女足出线形势
  • AddForceAtPosition方法:增加刚体点作用力
  • js对象值如何表示
  • 个体户税务三方协议必须签吗
  • 江苏省税务局电话咨询热线
  • 免责声明:网站部分图片文字素材来源于网络,如有侵权,请及时告知,我们会第一时间删除,谢谢! 邮箱:opceo@qq.com

    鄂ICP备2023003026号

    网站地图: 企业信息 工商信息 财税知识 网络常识 编程技术

    友情链接: 武汉网站建设