笔记-python-常见特殊变量

  • 类似__xx,以双下划线开头的实例变量名,就变成了一个私有变量(private),只有内部可以访问,外部不能访问;
  • 类似__xx__,以双下划线开头,并且以双下划线结尾的,是特殊变量,特殊变量是可以直接访问的,它不是private变量,下面会介绍Python中的常见特殊变量;
  • 类似_x,以单下划线开头的实例变量名,这样的变量外部是可以访问的,但是,按照约定俗成的规定,当你看到这样的变量时,意思就是,“虽然我可以被访问,但是请把我视为私有变量,不要随意访问”。

特殊变量

__doc__

定义文档字符串

__dict__

类的属性列表

__class__

__slots__

对类的实例可以动态的绑定属性和方法,如下:

from types import MethodType

def set_age(self, age):
self.age = age class P(object):
pass p = P()
p.name = 'chenqi'
p.set_age = MethodType(set_age, p, P) p.set_age(31)
print p.name
print p.age

对一个实例添加的属性(或方法)仅在该实例有效,对其它实例不起作用。

如果想让添加的方法对所有实例都生效,可以绑定到类上:

P.set_age = MethodType(set_age, None, P)

最后,__slots__的作用就是限制对类动态绑定的属性范围,例如:

class P(object):
__slots__ = ("name", "age")
pass

如上,除了"name"和"age"之外的属性就不能再增加了;

注意:__slots__属性不会继承给子类,仅在当前类生效。

__init__

创建实例的时候,可以调用__init__方法做一些初始化的工作:

class Student(object):
def __init__(self, name, score):
self.name = name
self.score = score def print_score(self):
print('%s: %s' % (self.name, self.score))

与普通的实例方法类似,如果子类不重写__init__,实例化子类时,会自动调用父类的__init__;

如果子类重写了__init__,实例化子类时,则只会调用子类的__init__,此时如果想使用父类的__init__,可以使用super函数,如下:

class P(object):
def __init__(self, name, score):
self.name = name
self.score = name class C(P):
def __init__(self, name, score, age):
super(C, self).__init__(name, score)
self.age = age c = C('cq', 100, 31)

__new__

注意:__init__是实例创建之后调用的第一个方法,而__new__更像构造函数,它在__init__之前被调用。

另外,__new__方法是一个静态方法,第一参数是cls,__new__方法必须返回创建出来的实例。

例如,用__new__实现单例模式:

class Singleton(object):
def __new__(cls):
# 关键在于这,每一次实例化的时候,我们都只会返回这同一个instance对象
if not hasattr(cls, 'instance'):
cls.instance = super(Singleton, cls).__new__(cls)
return cls.instance obj1 = Singleton()
obj2 = Singleton() obj1.attr1 = 'value1'
print obj1.attr1, obj2.attr1
print obj1 is obj2

__del__

类似析构函数。

class NewClass(object):
num_count = 0 def __init__(self,name):
self.name = name
self.__class__.num_count += 1
print name,NewClass.num_count def __del__(self):
self.__class__.num_count -= 1
print "Del",self.name,self.__class__.num_count a = NewClass("a")
b = NewClass("b")
c = NewClass("c") del a
del b
del c

注意:用del删除一个对象的时候,不一定会调用__del__,只有在对象的引用计数为零时,__del__()才会被执行。

__enter__

__exit__

这两个方法是用于支持with语句的上下文管理器。

例如让文件句柄支持with语法的实现:

class File(object):
def __init__(self, file_name, method):
self.file_obj = open(file_name, method)
def __enter__(self):
return self.file_obj
def __exit__(self, type, value, traceback):
self.file_obj.close() with File('demo.txt', 'w') as opened_file:
opened_file.write('Hola!')

__iter__

next

如果一个类想被用于for ... in循环,类似list或tuple那样,就必须实现一个__iter__()方法,该方法返回一个迭代对象,然后,Python的for循环就会不断调用该迭代对象的next()方法拿到循环的下一个值,直到遇到StopIteration错误时退出循环。

class Fib(object):
def __init__(self):
self.a, self.b = 0, 1 # 初始化两个计数器a,b def __iter__(self):
return self # 实例本身就是迭代对象,故返回自己 def next(self):
self.a, self.b = self.b, self.a + self.b # 计算下一个值
if self.a > 100000: # 退出循环的条件
raise StopIteration();
return self.a # 返回下一个值

__call__

实例可以像函数一样调用。

class Student(object):

    def __init__(self):
self.name = "Michael" def __call__(self):
print '__call__ called' s = Student()
s()

注意:callable()函数可用于判断一个对象是否可调用!

__str__,返回用户看到的字符串

__repr__,返回开发者看到的字符串(用于调试)

# test.py
class P(object):
def __str__(self):
return "__str__ called" def __repr__(self):
return "__repr__ called" p = P()

可以看下__str__和__repr__的区别:

>>> from test import p
>>> p
__repr__ called
>>> print p
__str__ called

__getitem__

__setitem__

__delitem__

支持下标(或切片)操作的函数,

例如:

class Fib(object):
def __getitem__(self, n):
if isinstance(n, int):
a, b = 1, 1
for x in range(n):
a, b = b, a + b
return a
if isinstance(n, slice):
start = n.start
stop = n.stop
a, b = 1, 1
L = []
for x in range(stop):
if x >= start:
L.append(a)
a, b = b, a + b
return L fib = Fib()
print fib[10]
print fib[0:10]

__getattr__

__getattribute__

__setattr__

__delattr__

支持点操作(即 "对象.属性" 访问方式),

当访问不存在的属性时,才会使用__getattr__  方法.

class Student(object):

    def __init__(self):
self.name = "Michael" def __getattr__(self, attr):
print '__getattr__ called'
if attr=='score':
return 99
elif attr=='name':
return "Tom" s = Student()
print s.score # 99
print s.name # Michael

Python的字典支持下标操作,但不支持 "." 操作,如果想让其支持,如下实现:

class Storage(dict):
__slots__ = ()
"""
A Storage object is like a dictionary except `obj.foo` can be used
in addition to `obj['foo']`. >>> o = Storage(a=1)
>>> o.a
1
>>> o['a']
1
>>> o.a = 2
>>> o['a']
2
>>> del o.a
>>> o.a
Traceback (most recent call last):
...
AttributeError: 'a'
>>> 'b' in o
False """ def __getattr__(self, key):
try:
return self[key]
except KeyError, k:
raise AttributeError(k) def __setattr__(self, key, value):
self[key] = value def __delattr__(self, key):
try:
del self[key]
except KeyError, k:
raise AttributeError(k) def __repr__(self):
return '<Storage ' + dict.__repr__(self) + '>'

引用文档:

https://www.cnblogs.com/chenny7/p/7338502.html

笔记-python-常见特殊变量的更多相关文章

  1. Python基础笔记系列九:变量、自定义函数以及局部变量和全局变量

    本系列教程供个人学习笔记使用,如果您要浏览可能需要其它编程语言基础(如C语言),why?因为我写得烂啊,只有我自己看得懂!! 变量在前面的系列中也许就可以发现,python中的变量和C中的变量有些许不 ...

  2. 学习Python笔记---变量和简单数据类型

    首先声明,这个是个人在自学的一些笔记,因为是小白,刚接触Python,之前也没有过类似的经验,所以很多东西对于其他人来说可能是小白级别的,写出来没有其他的意思就是自己整理然后记录一下,顺便分享出来,而 ...

  3. Python学习笔记一:第一个Python程序,变量,字符编码与二进制,用户交互程序

    第一个python程序 Windows:设置环境变量,X:\pthonxxx,xxx是版本号 在命令提示符下 输入python,进入解释器 >>>print(“Hello World ...

  4. Python学习笔记 (2)变量、常量和数据类型

    变量 顾名思义,变量就是一个会变的量,用一个变量名表示,指向内存中一片区域,而指向的区域存的是什么,这个变量就是什么数据类型,和C/C++挺不一样的.变量数据类型可以通过赋值变来变去(这就叫动态语言, ...

  5. python中的变量和数据类型

    一.变量定义:变量是计算机内存中的一块区域,存储规定范围内的值,值 可以改变,通俗的说变量就是给数据起个名字. 二.变量命名规则: 1. 变量名由字母.数字.下划线组成 2. 数字不能开头 3. 不可 ...

  6. Python常见的错误汇总

    +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 错误: [错误分析]第二个参数必须为类,否则会报TypeError,所以正确的应 ...

  7. python中的变量与对象

    一. 什么是变量 变量就是以前学习的数学中常见的等式x = 3(x是变量,3是变量值),在编程中,变量不仅可以是数学,还可以是任意数据类型 二. 变量的命名规则 变量名必须是英文大小写.数字和_的组合 ...

  8. 笔记-python lib-pymongo

    笔记-python lib-pymongo 1.      开始 pymongo是python版的连接库,最新版为3.7.2. 文档地址:https://pypi.org/project/pymong ...

  9. 笔记-python tutorial-9.classes

    笔记-python tutorial-9.classes 1.      Classes 1.1.    scopes and namespaces namespace: A namespace is ...

随机推荐

  1. Eclipse集成Maven(手工安装Maven且手工集成到Eclipse)

    1.操作环境 操作系统:win8 64位 IDE:Helios Eclipse 1.8 JDK:1.6 2.资源准备 2.1 maven安装包: apache-maven-3.2.5-bin.zip  ...

  2. diskpart分区

    分区知识充电: 主分区:主分区,也称为主磁盘分区,和拓展分区.逻辑分区一样,是一种分区类型.主分区中不能再划分其他类型的分区,因此每个主分区都相当于一个逻辑磁(在这一点上主分区和逻辑分区很相似,但主分 ...

  3. 微信小程序开发实践

    目录 项目是否适合移植到小程序上? 概要介绍 实践得到的经验 规则 小程序不支持的 新特性 小窍门 会话管理 进阶 项目是否适合移植到小程序上? 小程序由于微信提供了一些组件,在微信中的一些体验确实不 ...

  4. leetcode 198、打家劫舍

    You are a professional robber planning to rob houses along a street. Each house has a certain amount ...

  5. 【洛谷5294】[HNOI2019] 序列(主席树维护单调栈+二分)

    点此看题面 大致题意: 给你一个长度为\(n\)的序列\(A\),每次询问修改一个元素(只对当前询问有效),然后让你找到一个不下降序列\(B\),使得这两个序列相应位置之差的平方和最小,并输出这个最小 ...

  6. mac下登录服务器

    1.先通过帐号密码登录到服务器: ssh 用户名@服务器地址 https://jingyan.baidu.com/article/546ae1853132bf1148f28c42.html 2.登录后 ...

  7. 【luogu P1821 [USACO07FEB]银牛派对Silver Cow Party】 题解

    题目链接:https://www.luogu.org/problemnew/show/P1821 反向多存一个图,暴力跑两遍 #include <cstdio> #include < ...

  8. EJB结合struts2创建项目、发布jboss服务器和访问、父类(BaseDaoImpl)的封装

    一.环境搭建: 1.准备jboss服务器,将对应数据库的xml配置好放到jboss的发布目录下. <?xml version="1.0" encoding="UTF ...

  9. 【题解】洛谷P1262 间谍网络 (强连通分量缩点)

    洛谷P1262:https://www.luogu.org/problemnew/show/P1262 思路 一看题目就知道是强连通分量缩点 当图中有强连通分量时 将其缩点 我们可以用dfn数组判断是 ...

  10. An error occurred during the installation of assembly 'Microsoft.VC90.ATL or 'Microsoft.VC80.ATL'

    An error occurred during the installation of assembly 'Microsoft.VC90.ATL or 'Microsoft.VC80.ATL' 下载 ...