python中几个常见的魔法方法
首先,什么是魔法方法呢?在python中方法名如果是__xxxx__()的,那么就有特殊的功能,因此叫做“魔法”方法。
__ init__()方法
- 当一个实例被创建的时候调用的初始化方法,在创建对象时默认调用。
- __ init __()方法中默认有一个参数名字为self,如果在创建对象时传递了2个参数,那么__init __()方法除了self作为第一个形参外还需要2个形参,例如__init __(self,x,y)。
之前我们是这样给对象添加属性的:
class Student:
pass
stu1 = Student()
stu1.name = "张三"
stu1.age = 18
现在我们利用__init__()方法简化代码
class Student:
def __init__(self, name, age):
self.name = name
self.age = age
stu1 = Student("张三", 18)
是不是代码看起来简洁多了呢
__str __()方法
- 一般用于说明对象,或者自己定义一个想要输出的结果。
- 当调用str()时会调用__str __(),即该对象被强制转换成字符串类型。
- 当使用print()输出该对象时也会调用__str __()方法,只要自己定义了__str __()方法,那么就会打印这个方法中return中的数据。
没有定义__str __()方法时:
class Student:
def __init__(self, name, age):
self.name = name
self.age = age
stu1 = Student("张三", 18)
print(stu1)
s = str(stu1)
print(s)
"""
输出结果:
<__main__.Student object at 0x03C3BCD0>
<__main__.Student object at 0x03C3BCD0>
"""
没有定义__str __()方法时,它默认返回该对象的内存地址。
定义了__str __()方法是这样的:
class Student:
def __init__(self, name, age):
self.name = name
self.age = age
def __str__(self):
return "姓名:%s\t年龄:%d"%(self.name, self.age)
stu1 = Student("张三", 18)
print(stu1)
s = str(stu1)
print(s)
"""
输出结果:
姓名:张三 年龄:18
姓名:张三 年龄:18
"""
__del __()方法
当删除一个对象时,python解释器会默认调用一个方法,这个方法为__del__()方法。
首先应该先了解一个概念,那就是对象的引用个数。我们需要sys模块中的getrefcount()用来测量一个对象的引用个数,返回值=实际的引用个数+1。若返回2则说明该对象的实际引用个数为1,此时有1个变量引用了该对象。
import sys
class A:
pass
a = A()
# 现在只有变量a引用了A类创建的对象
print(sys.getrefcount(a))
"""
输出结果:
2
"""
# 那么现在再创建一个变量b,也引用a所引用的对象,那么它的引用个数就会加1,实际引用个数变成2.
b = a
print(sys.getrefcount(a))
"""
输出结果:
3
"""
当python解释器检测到,这个对象的实际引用个数为0时,就会删除这个对象,此时也就会相应的调用__del __()方法。还有一种情况就是该程序已经全部执行完了,那么相应的内存会被释放掉,它也会执行__del __()方法。
这是程序正常执行完的情况:
import sys
class A:
def __del__(self):
print("该对象被销毁")
a = A()
"""
输出结果:
该对象被销毁
"""
还有一种是手动删除变量引用的情况:
import sys
class A:
def __del__(self):
print("该对象被销毁")
a = A() # 此时实际引用个数为1
b = a # 此时实际引用个数为2
print("删除了变量a")
del a # 删除变量a,此时实际引用个数为1
print("删除了变量b")
del b # 删除变量b,此时实际引用个数为0,python解释器就会删除该对象,即调用__del __()方法
print("程序结束")
"""
输出结果:
删除了变量a
删除了变量b
该对象被销毁
程序结束
"""
__new __()方法
- __new __也是类在创建实例时调用的方法,它比__init __调用的时间还早。
- __new __至少要有一个参数cls,代表要实例化的类,此参数在实例化时由python解释器自动提供。
- __new __必须要有返回值,返回实例化出来的实例,这点在自己实现__new__时要特别注意,可以return父类__new__出来的实例,或者直接是object的__new__出来的实例。在Python3中每个类都默认继承的object父类。
- __init__有一个参数self,就是这个__new__返回的实例,__init__在__new__的基础上可以完成一些其它初始化的动作,__init__不需要返回值
class A:
def __init__(self):
print("调用了init方法")
def __new__(cls):
print("调用了new方法")
return super().__new__(cls)
a = A()
"""
输出结果:
调用了new方法
调用了init方法
"""
拓展:可以通过重写__new __方法,实现一个单例模式
代码如下:
class A:
# 定义一个私有的类属性,用于存储实例化出来的对象
_isinstance = None
def __new__(cls):
print("调用了new方法")
# 判断如果_isinstance为None,则创建一个实例,否则直接返回_isinstance
if not cls._isinstance:
cls._isinstance = super().__new__(cls)
return cls._isinstance
print(id(A))
print(id(A))
print(id(A))
print(id(A))
"""
输出结果:
19888488
19888488
19888488
19888488
"""
__slots __属性
我们都知道python是一门动态语言,可以在程序运行的过程中添加属性。如果我们想要限制实例的属性该怎么办?例如,只允许对Person实例添加name和age属性。
为了达到限制的⽬的,Python允许在定义class的时候,定义⼀个特殊的 __slots__变量,来限制该class实例能添加的属性:
class Person(object):
__slots__ = ("name", "age")
P = Person()
P.name = "⽼王"
P.age = 20
P.score = 100
"""
输出结果:
Traceback (most recent call last):
File "<input>", line 6, in <module>
AttributeError: 'Person' object has no attribute 'score'
"""
注意:使⽤__slots__要注意,__slots__定义的属性仅对当前类实例起作⽤,对 继承的⼦类是不起作⽤的。
python中几个常见的魔法方法的更多相关文章
- python中的魔术属性与魔法方法
1.魔法属性 · 1.1__doc__魔法属性 表示类的描述信息 class Fo: """ 这是今天第一个魔术属性__doc__""" ...
- 面向对象相关概念与在python中的面向对象知识(魔法方法+反射+元类+鸭子类型)
面向对象知识 封装 封装的原理是,其成员变量代表对象的属性,方法代表这个对象的动作真正的封装是,经过深入的思考,做出良好的抽象(设计属性时用到),给出“完整且最小”的接口,并使得内部细节可以对外透明( ...
- Python中执行系统命令常见的几种方法--转载
Python中执行系统命令常见的几种方法 Python中执行系统命令常见的几种方法有: (1)os.system # 仅仅在一个子终端运行系统命令,而不能获取命令执行后的返回信息 # 如果再命令行下执 ...
- python中常用的九种预处理方法
本文总结的是我们大家在python中常见的数据预处理方法,以下通过sklearn的preprocessing模块来介绍; 1. 标准化(Standardization or Mean Removal ...
- Python中异步协程的使用方法介绍
1. 前言 在执行一些 IO 密集型任务的时候,程序常常会因为等待 IO 而阻塞.比如在网络爬虫中,如果我们使用 requests 库来进行请求的话,如果网站响应速度过慢,程序一直在等待网站响应,最后 ...
- 举例详解Python中的split()函数的使用方法
这篇文章主要介绍了举例详解Python中的split()函数的使用方法,split()函数的使用是Python学习当中的基础知识,通常用于将字符串切片并转换为列表,需要的朋友可以参考下 函数:sp ...
- Python中os和shutil模块实用方法集…
Python中os和shutil模块实用方法集锦 类型:转载 时间:2014-05-13 这篇文章主要介绍了Python中os和shutil模块实用方法集锦,需要的朋友可以参考下 复制代码代码如下: ...
- Python中os和shutil模块实用方法集锦
Python中os和shutil模块实用方法集锦 类型:转载 时间:2014-05-13 这篇文章主要介绍了Python中os和shutil模块实用方法集锦,需要的朋友可以参考下 复制代码代码如下: ...
- Python中的str与unicode处理方法
Python中的str与unicode处理方法 2015/03/25 · 基础知识 · 3 评论· Python 分享到:42 原文出处: liuaiqi627 的博客 python2.x中处理 ...
随机推荐
- 【POJ1011】Sticks
[题目概括] 现在有\(n\)个长度不超过\(50\)的木棍,请你把这些小木棍拼成若干根长度相同的木棍. 请你最小化拼成后的长度. [思路要点] 考虑枚举最后的长度,然后判断是否可以,这样就不需要最优 ...
- 计蒜客T2202 数三角形(提高组2017模拟赛(三)day2T3) LZOJ3878攻略
今天模拟赛考了一道计蒜客NOIP2017模拟赛(三)day2T3的数三角形,原题链接 https://nanti.jisuanke.com/t/T2202 ,LZOJ3878攻略.场上想了很久都没转化 ...
- JS基础-连续赋值
重点:先声明,从左向右,声明变量分配内存,后赋值,从右向左 问题 var a = {n: 1}; var b = a; a.x = a = {n: 2}; console.log(a.x); cons ...
- LeetCode 第 3 题:无重复字符的最长子串(滑动窗口)
LeetCode 第 3 题:无重复字符的最长子串 (滑动窗口) 方法:滑动窗口 滑动窗口模板问题:右指针先走,满足了一定条件以后,左指针向前走,直到不满足条件. 特点:左右指针的方向是一致的,并且是 ...
- async/await 真不是你想象中那么简单
先上代码 公共代码 function getData(data, time) { return new Promise(function (resolve, reject) { setTimeout( ...
- 【学习】windows 下PostgreSQL导入sql文件
在软件的安装目录的bin文件下打开命令行工具 输入: psql -d 数据库名称 -h 数据库地址 -p 5432 -U postgres -f sql文件(E:\Config\SQL\iS ...
- MQTT消息中间件Mosquitto的安装和配置
特别提示:本人博客部分有参考网络其他博客,但均是本人亲手编写过并验证通过.如发现博客有错误,请及时提出以免误导其他人,谢谢!欢迎转载,但记得标明文章出处:http://www.cnblogs.com/ ...
- swift模式和模式匹配
模式和模式匹配 模式: 代表单个或者复合值得结构,也就是说模式不是一个特定的值,它是一种抽象的结构,[一句话,不是特指,是泛指].这样就可以用模式来匹配各种各样的值. 例如:(x,y)可以匹配元祖(1 ...
- MySQL学习笔记(cmd模式下的操作)
1.登入MySQL 1.1 登入MySQL 1.1.1命令如下: C:\Users\zjw>mysql -hlocalhost -uroot -p Enter password: ****** ...
- Java_IO流实验
实验题目链接:Java第09次实验(IO流) 0. 字节流与二进制文件 我的代码 package experiment.io; import java.io.DataInputStream; impo ...