[Dynamic Language] Python __slots__ 限制绑定属性

Python 是一门动态语言,可以在运行过程中,修改对象的属性和增删方法。任何类的实例对象包含一个字典__dict__, Python通过这个字典将任意属性绑定到对象上。有时候我们只想使用固定的对象,而不想任意绑定对象,这时候我们可以定义一个属性名称集合,只有在这个集合里的名称才可以绑定。__slots__就是完成这个功能的。

test code

1 #!/usr/bin/env python
2 #_*_ coding:utf-8 _*_
3
4 class test_slot(object):
5 __slots__ = "width", "height"
6
7 def width(self):
8 print "width"
9
10
11 class test(object):
12 def amethod(self):
13 print "amethod"

ipython执行代码导入

In [1]: from test import *
In [
2]: dir(test_slot)
Out[
2]:
[
'__class__',
'__slots__',
'__str__',
'height',
'width']

In [
3]: dir(test)
Out[
3]:
[
'__class__',
'__weakref__',
'amethod']

可以看到 test_slot 类结构里面已经有height和width属性了。

下面我们继续查看两个实例对象结构里都有什么吧

In [4]: s = test_slot()
In [
5]: t = test()

In [
11]: dir(s)
Out[
11]:
[
'__class__',
'__delattr__',
'__doc__',
'__slots__',
'height',
'width']

In [
12]: dir(t)
Out[
12]:
[
'__class__',
'__delattr__',
'__dict__',
'__doc__',
'amethod']

看到了吧, test_slot 的实例s 没有字典__dict__,多了__slots__属性,这样就不能任意绑定属性,只能绑定__slots__属性名称集合里的同名属性了。

我们来测试一把,先给两个实例的赋__slots__里面有的 height 属性,当然对t来说是新加属性。

In [7]: s.height = 1
In [8]: t.height = 0

赋值都没有问题。

下面再试一下不在__slots__里的属性名.

In [9]: s.abeen = "abeen" //和预期的一样,失败了。
---------------------------------------------------------------------------
AttributeError Traceback (most recent call last)

/home/abeen/learn_test/test/<ipython console> in <module>()

AttributeError:
'test_slot' object has no attribute 'abeen'

In [
10]: t.abeen = "abeen" //正常运行
原文地址:https://www.cnblogs.com/abeen/p/1936729.html