Python实例属性限制(__slots__)
Python的动态绑定可以在程序运行的过程中对实例或class加上功能,但是如果我们想要限制实例的属性怎么办呢?更改内容请参考:Python学习指南
正常情况下,当我们定义了一个class,创建了一个class实例后,我们可以给该实例绑定任何属性和方法,这就是动态语言的灵活性。先定义class:
class Student(object):
pass
然后,尝试给实例绑定一个属性:
s = Student()
s.name = 'Michael'
print(s.name)
Michael
还可以给实例绑定一个方法:
def set_age(self, age): #定义一个函数作为实例方法
self.age = age
from types import MethodType
s.set_age = MethodType(set_age, s) #给实例绑定一个方法
s.set_age(25)
s.age
25
但是,给一个实例绑定的方法,对另一个实例是不起作用的:
s2 = Student() #创建一个新的实例
s2.set_age(25)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: 'Student' object has no attribute 'set_age'
为了给所有实例都绑定方法,可以给class绑定方法:
def set_score(self, score):
self.score = score
Student.set_score = set_score
给class绑定方法后,所有实例均可调用:
s.set_score(100)
s.score
100
s2.set_score(99)
s2.score
99
只要在class上绑定方法以后,实例就可以直接使用了。
通常情况下,上面的set_score
方法可以直接定义在class中,但动态绑定允许我们在程序运行的过程中动态给class加上功能,这在静态语言中很难实现。
使用__slots__
但是,如果我们想要限制实例的属性怎么办?比如,只允许对Student实例添加name
和age
实现。
为了达到限制的目的,Python允许在定义class的时候,定义一个特殊的变量__slots__
变量,来限制该class实例能添加的属性:
class Student(object):
__slots__ = ('name', 'age') #用tuple定义允许绑定的属性名称
然后,我们试试:
>>> s = Student() # 创建新的实例
>>> s.name = 'Michael' # 绑定属性'name'
>>> s.age = 25 # 绑定属性'age'
>>> s.score = 99 # 绑定属性'score'
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: 'Student' object has no attribute 'score'
>>>Student.score = 100
>>>s.score
100
由于'score'没有被放到__slots__
中,所以不能绑定score
属性,试图绑定score
将得到AttributeError
的错误。但是可以对class类添加属性,__slots__
只是限制实例添加的属性,但类属性管不了。
使用__slots__
要注意,__slots__
定义的属性仅对当前类实例起作用,对继承的子类是不起作用的:
class GraduteStudent(Student):
pass
g = GraduteStudent()
s.score = 99
除非在子类中也定义__slots__
,这样,子类实例允许定义的属性就是自身的__slots__
加上父类的__slots__
。
Python实例属性限制(__slots__)的更多相关文章
- python:实例属性和类属性
由于Python是动态语言,根据类创建的实例可以任意绑定属性. 给实例绑定属性的方法是通过实例变量,或者通过self变量: class Student(object): def __init__(se ...
- python 实例属性
>>> class a(object): pass >>> o=a() >>> o.a='ok'#直接给实例添加属性,调用了__setattri_ ...
- python 实例属性之单,双下划线
具体区别看下面例子 class A: def __init__(self,name='Andy'): self._name = name class B: def __init__(self,name ...
- python基础——实例属性和类属性
python基础——实例属性和类属性 由于Python是动态语言,根据类创建的实例可以任意绑定属性. 给实例绑定属性的方法是通过实例变量,或者通过self变量: class Student(objec ...
- Python之实例属性和类属性
参考原文 廖雪峰Python 实例属性和类属性 在前面已经说过由于Python是动态语言,可以根据类的实例绑定任何的属性. 给实例绑定属性的方法是通过实例变量,或者self变量绑定的: class S ...
- Python笔记(十八)_私有属性、实例属性、类属性
私有属性 如果要让内部属性不被外部访问,可以把属性的名称前加上两个下划线__,就变成了一个私有属性,只有内部可以访问,外部不能直接访问或修改. 这样就确保了外部代码不能随意修改对象内部的状态,这样通过 ...
- 【Python】[面性对象编程] 获取对象信息,实例属性和类属性
获取对象信息1.使用isinstance()判断class类型2.dir() 返回一个对象的所有属性和方法3.如果试图获取不存在的对象会抛出异常[AttributeError]4.正确利用对象内置函数 ...
- Python类的实例属性详解
实例属性 1.类被实例化后才会具有的属性 2.一般在_init_()方法中创建并初始化 3.直接使用即定义:self.<属性名> 4.引用方法:self.<属性名> 5.sel ...
- Python类属性,实例属性
1.Python类数据属性:定义在类里面但在函数外面的变量,它们都是静态的. #一段很简单的代码,但反应了很多 >>> class A(): a=1 #一个类里面有个属性a > ...
随机推荐
- java中String的equals()和 ==
String a=new String("java"); String b=new String("java"); System.out.println(a.e ...
- jmeter中测试接口
本文主要介绍在jmeter中测试接口:主要从以下几个方面进行说明: 1.jmeter简介 2.jmeter怎么做接口测试 3.jmeter进行参数化的几种形式 4.jmeter中处理乱码方法 5.jm ...
- Oracle中从控制文件读取的视图
Oracle中有一些数据字典视图需从控制文件中读取信息,如下所示.用户在数据库打开之前就可以访问这些视图,因为这些视图的内容存储在控制文件中. v$archived_log:归档日志信息,如大小,SC ...
- C代码与C++代码之间的相互调用
1.showCpp.cpp #include <iostream> using namespace std; // 声明为C语言可以调用的函数 extern "C" v ...
- Node.js 回调函数 1) 阻塞 ,同步 2) 非阻塞 ,异步.
1.阻塞. 同步. 1) 读取的文件: input.txt 菜鸟教程官网地址:www.runoob.com 2) main.js var fs = require("fs"); / ...
- Beta阶段复审
名字 优点 缺点 排名 都行可以随它去 1.界面美观,比较的友好: 2.新增记账的邮箱提醒功能. 1.程序有什么具体的bug和或缺陷?(1)没有账单删除的功能:(2)预算没有什么必要.2.项目的目标实 ...
- kbmMWLog输出日志到控制台或指定Grid
刚看到有人在kbmMW News问,有没有简单的方法,输出日志到Console窗口或者一个实际的Grid? 作者对此做回复,大意是这样: 对于输出日志到一个Memo,使用TkbmMWStringsLo ...
- diary of laravel
1. 修改数据库连接 初始化数据库: 首先: 修改 config- database.php 中的 数据库链接 其次:修改 .env 中数据库链接 创建表: php artisan migr ...
- 启动apache 找不到 mbstring.dll
启动appserv时 提示 无法启动此程序 因为计算机中丢失php mbstring.dll 这种原因一般都是组件加载顺序引起的,在php.ini文件里确保 extension=php_mbstr ...
- react-native-echarts 解决数据刷新闪烁,不能动态连续绘制问题(转载)
最终能实现效果:动态绘制K线图,安卓,iOS正常显示 替换node_modules/native-echarts/src/components/Echarts/中的index.js和renderCha ...