Python描述符以及Property方法的实现原理
Python描述符以及Property方法的实现原理
描述符的定义:
描述符是什么:描述符本质就是一个新式类,在这个新式类中,至少实了__get__(),__set__(),__delete__()中的一个,这也被称为描述符协议
__get__():调用一个属性时,触发
__set__():为一个属性赋值时,触发
__delete__():采用del删除属性时,触发
描述符作用:
描述符的作用是用来代理另外一个类的属性的(必须把描述符定义成这个类的类属性,不能定义到构造函数中)
可以说成是属性的属性,定义属性的属性
描述符本身的实例并不会触发这三个方法
class dis:
def __set__(self, instance, value):
print('正在执行__set__方法.....')
def __delete__(self, instance):
print('正在执行__delete__方法')
def __get__(self, instance, owner):
print('正在执行__get__方法')
d = dis()
d.name = "1"
print(d.name)
del d.name
#================输出===================
1
描述符解析
分析代码
class dis:
def __init__(self, fget, fset, fdel):
self.fget = fget
self.fset = fset
self.fdel = fdel
print('正在执行__init__方法.....')
def __set__(self, instance, value):
print('正在执行__set__方法.....')
print(instance, value)
def __delete__(self, instance):
print('正在执行__delete__方法')
print(instance)
def __get__(self, instance, owner):
print('正在执行__get__方法')
print(instance, owner)
class test:
def __init__(self, value = 10):
self.value = value
def fset(self, value):
self.value = value
def fget(self):
return self.value
def fdel(self):
del self.value
x = dis(fget, fset, fdel)
t = test()
print(t.x)
t.x = 20
print(t.x)
del t.x
输出
正在执行__init__方法.....
正在执行__get__方法
<__main__.test object at 0x0000016CA299CEE0> <class '__main__.test'>
None
正在执行__set__方法.....
<__main__.test object at 0x0000016CA299CEE0> 20
正在执行__get__方法
<__main__.test object at 0x0000016CA299CEE0> <class '__main__.test'>
None
正在执行__delete__方法
<__main__.test object at 0x0000016CA299CEE0>
当test类试图去通过x属性来访问自身的value属性时,就会自动跳转到执行dis类里面的__get__方法。
当试图通过x去修改value的属性时就会执行dis类里面的__set__方法。
当试图通过x去删除value的属性时会执行dis类里面的__del__方法。
然后我把它们的参数类型打印出来可以知道;
instance参数指的是test类的实例化对象t;
owner指的是test类;
因为这几个方法我只是把值给打印出来,并未给出有效操作的代码,就返回值一直是None知道了上面之后我们可以实现property方法。
class dis:
def __init__(self, fget = None, fset = None, fdel = None):
self.fget = fget
self.fset = fset
self.fdel = fdel
def __set__(self, instance, value):
self.fset(instance, value)#这里fset的参数类型看test里面的fset就行,鸭子类型
def __delete__(self, instance):
self.fdel(instance)
def __get__(self, instance, owner):
return self.fget(instance)
以上大概就是property方法,然后再加上测试的代码
class test:
def __init__(self, value = 10):
self.value = value
def fset(self, value):
self.value = value
def fget(self):
return self.value
def fdel(self):
del self.value
x = dis(fget, fset, fdel)
t = test()
print(t.x)
t.x = 20
print(t.x)
del t.x
try:
print(t.x)
except AttributeError as reason:
print("出错啦"+str(reason))
这里是输出结果:
10
20
出错啦'test' object has no attribute 'value'
Python描述符以及Property方法的实现原理的更多相关文章
- Python描述符:property()函数的小秘密
描述符:将某种特殊类型的类的实例指派给另一个类的属性(注意:这里是类属性,而不是对象属性).而这种特殊类型的类就是实现了__get__,__set__,__delete__这三个方法中的一个或多个的新 ...
- python描述符(descriptor)、属性(property)、函数(类)装饰器(decorator )原理实例详解
1.前言 Python的描述符是接触到Python核心编程中一个比较难以理解的内容,自己在学习的过程中也遇到过很多的疑惑,通过google和阅读源码,现将自己的理解和心得记录下来,也为正在为了该问题 ...
- 课时46:魔法方法:描述符(property的原理)
目录: 一.描述符(property的原理) 二.课时46课后习题及答案 ********************************** 一.描述符(property的原理) ********* ...
- 【转载】Python 描述符简介
来源:Alex Starostin 链接:www.ibm.com/developerworks/cn/opensource/os-pythondescriptors/ 关于Python@修饰符的文章可 ...
- Python描述符的使用
Python描述符的使用 前言 作为一位python的使用者,你可能使用python有一段时间了,但是对于python中的描述符却未必使用过,接下来是对描述符使用的介绍 场景介绍 为了引入描述符的使用 ...
- python描述符学习
目录 一.对象属性的访问控制 二.描述符基本理解 三.基本使用 四.使用描述符完成property.classmethod.staticmethod自定义实现 1.property的自定义实现 2.c ...
- Python 描述符 (descriptor)
1.什么是描述符? 描述符是Python新式类的关键点之一,它为对象属性提供强大的API,你可以认为描述符是表示对象属性的一个代理.当需要属性时,可根据你遇到的情况,通过描述符进行访问他(摘自Pyth ...
- 杂项之python描述符协议
杂项之python描述符协议 本节内容 由来 描述符协议概念 类的静态方法及类方法实现原理 类作为装饰器使用 1. 由来 闲来无事去看了看django中的内置分页方法,发现里面用到了类作为装饰器来使用 ...
- python描述符理解
Python中的描述符是一个相对底层的概念 descriptor Any object which defines the methods get(), set(), or delete(). Whe ...
随机推荐
- 【UE4 C++】抛物线路径、发射轨道相关
基于UGameplayStatics Blueprint_PredictProjectilePath_ByObjectType 根据 Object Type,算出抛物线的点集合和检测结果 static ...
- 关于java socket中的read方法阻塞问题
客户端: public class TCPClient { public static void main(String[] args) throws IOException { FileInputS ...
- JVM:内存模型
JVM:内存模型 说明:这是看了 bilibili 上 黑马程序员 的课程 JVM完整教程 后做的笔记 1. java 内存模型 很多人将[java 内存结构]与[java 内存模型]傻傻分不清,[j ...
- Sharding-JDBC自定义复合分片算法
Sharding-JDBC自定义复合分片算法 一.背景 二.需求 1.对于客户端操作而言 2.对于运营端操作而言 三.分片算法 1.客户id和订单id的生成规则 2. 确定数据落在那个表中 3.举例说 ...
- 攻防世界 杂项 4.something_in_image
这是原题 我这里使用编辑器打开,一看乱码也挺多的,于是想了想ctrl+f搜索一下flag关键字吧,结果答案出来了(flag不少,多搜索几次) Flag{yc4pl0fvjs2k1t7T}
- 在Ubuntu下安装Solr
使用wget命令去官网下载solr的压缩包. 1 wget https://mirrors.bfsu.edu.cn/apache/lucene/solr/8.6.3/solr-8.6.3.tgz 使用 ...
- createContext 你用对了吗?
目录 前言 性能问题的根源 问题1(整体重复渲染):Provider组件包裹的子组件全部渲染 问题2(局部重复渲染):使用useContext导致组件渲染 解决方案 解决问题1 解决问题2 参考 前言 ...
- 『学了就忘』Linux基础 — 16、Linux系统与Windows系统的不同
目录 1.Linux严格区分大小写 2.Linux一切皆文件 3.Linux不靠扩展名区分文件类型 4.Linux中所有的存储设备都必须在挂载之后才能使用 5.Windows下的程序不能直接在Linu ...
- Redis源码分析(dict)
源码版本:redis-4.0.1 源码位置: dict.h:dictEntry.dictht.dict等数据结构定义. dict.c:创建.插入.查找等功能实现. 一.dict 简介 dict (di ...
- FAIL : Keyword 'BuiltIn.Log' expected 1 to 6 arguments, got 12(解决方法)
RF运行关键字:Run Keyword If ,log输出报错"FAIL : Keyword 'BuiltIn.Log' expected 1 to 6 arguments, got 12. ...