python中的__del__()方法

函数中的 __del__()  方法: 销毁对象

Python通过调用__init__()方法构造当前类的实例化对象,而__del__()方法,是用来销毁实例化对象。

事实上在编写程序时,如果之前我们创建的类实例化对象后续不再使用,最好再合适位置手动将其销毁,释放其占用的内存空间(整个过程称为垃圾回收(简称:GC))

大多数情况下,Python开发者不需要手动进行垃圾回收,因为Python有自动的垃圾回收机制,能将不需要使用的实例对象进行销毁

(pycharm环境,python3.7.6)

实例一

# -*- coding:utf8 -*-classUser:

def__init__(self):

print("=== 调用 __init__() 方法构造对象 ===")

def__del__(self):

print("调用__del__() 销毁对象,(对象占用的内存被回收)")

u1=User()

print('#'*50)

运行结果:

D:\pythonproject\venv\Scripts\python.exe D:/pythonproject/私有属性2.py

=== 调用 __init__() 方法构造对象 ===

##################################################

调用__del__() 销毁对象,(对象占用的内存被回收)

Process finished with exit code 0

注释:上面代码在交互式python下运行是不会调用__del__()方法的,也就不会打印出调用__del__() 销毁对象,(对象占用的内存被回收)

结论:Python 会在程序即将结束前调用__del__方法,自动帮我们销毁对象,进而释放对象占用的内存,注意__del__()方法调用的位置,在print('#'*50)语句之后。

实例二

# -*- coding:utf8 -*-classUser:

def__init__(self):

print("=== 调用 __init__() 方法构造对象 ===")

def__del__(self):

print("调用__del__() 销毁对象,(对象占用的内存被回收)")

u1=User()

delu1print('#'*50)

运行结果:

D:\pythonproject\venv\Scripts\python.exe D:/pythonproject/私有属性2.py

=== 调用 __init__() 方法构造对象 ===

调用__del__() 销毁对象,(对象占用的内存被回收)

##################################################

Process finished with exit code 0

结论:手动删除对象,进而调用 __del__() 方法销毁内存对象,释放内存空间

实例三

# -*- coding:utf8 -*-classUser:

def__init__(self):

print("=== 调用 __init__() 方法构造对象 ===")

def__del__(self):

print("调用__del__() 销毁对象,(对象占用的内存被回收)")

u1=User()

# 添加一个引用u1对象的实例对象u2=u1delu1#print('#'*50)

运行结果:

D:\pythonproject\venv\Scripts\python.exe D:/pythonproject/私有属性2.py

=== 调用 __init__() 方法构造对象 ===

##################################################

调用__del__() 销毁对象,(对象占用的内存被回收)

Process finished with exit code 0

结论:从运行结果可以看出来,执行该语句 del u1 调用 __del__()方法,但是并没有立即执行,而是在程序即将运行结束的时候,程序自动调用了__del__()方法,销毁了内存对象,这里涉及Python的垃圾回收机制

Python采用自动引用计数(简称:ARC(auto-refrence-count))的方式实现垃圾回收机制。该方法的核心思想是:每一个Python对象都会配置一个计数器,初始Python实例对象的计数器值都为0,如果有变量引用该实例对象,其计数器的值也会加1,依次类推;反之,每当一个变量取消对该实例对象的引用,计数器会减1。如果一个Python对象的计数器值为0,则表明没有变量引用该Python对象,即证明程序不再需要它了,此时Python就会自动调用__del__()方法将其回收

以实例二为例:实际上构建u1实例对象的过程分为2步,先使用User()调用该类中的__init__()方法构造出一个该类的对象(我们将其称为U,计数器为0),并立即用 u1 这个变量作为所建实例对象的引用 (U 的计数器值 + 1)。在此基础上,又有一个 u2 变量引用 u1(其实相当于引用User(),此时U的计数器再 +1),这时如果调用 del u1 语句,只会导致 C 的计数器减 1(值变为1),因此C的计数器值不为0,因此U不会被销毁(不会执行 __del__() 方法)。

实例四 1.0

# -*- coding:utf8 -*-classUser:

def__init__(self):

print("=== 调用 __init__() 方法构造对象 ===")

def__del__(self):

print("调用__del__() 销毁对象,(对象占用的内存被回收)")

u1=User()

u2=u1# del u1 # 从运行结果可以看出来,执行该语句没有调用 __del__()方法,而是在程序即将运行结束的时候,程序自动调用了__del__()方法,销毁了对象# print('#'*50)# print('\n')# del u2# print("*"*50)

运行结果:

D:\pythonproject\venv\Scripts\python.exe D:/pythonproject/私有属性2.py

===调用 __init__() 方法构造对象===调用__del__() 销毁对象,(对象占用的内存被回收)

Process finished withexitcode0

实例四 1.1:

# -*- coding:utf8 -*-classUser:

def__init__(self):

print("=== 调用 __init__() 方法构造对象 ===")

def__del__(self):

print("调用__del__() 销毁对象,(对象占用的内存被回收)")

u1=User()

u2=u1delu1# 从运行结果可以看出来,执行该语句没有调用 __del__()方法,而是在程序即将运行结束的时候,程序自动调用了__del__()方法,销毁了对象print('#'*50)

# print('\n')# del u2print("*"*50)

运行结果:

D:\pythonproject\venv\Scripts\python.exe D:/pythonproject/私有属性2.py

=== 调用 __init__() 方法构造对象 ===

##################################################

**************************************************

调用__del__() 销毁对象,(对象占用的内存被回收)

Process finished with exit code 0

实例四 1.2:

# -*- coding:utf8 -*-classUser:

def__init__(self):

print("=== 调用 __init__() 方法构造对象 ===")

def__del__(self):

print("调用__del__() 销毁对象,(对象占用的内存被回收)")

u1=User()

u2=u1delu1# 从运行结果可以看出来,执行该语句没有调用 __del__()方法,而是在程序即将运行结束的时候,程序自动调用了__del__()方法,销毁了对象print('#'*50)

print('\n')

delu2print("*"*50)

运行结果:

D:\pythonproject\venv\Scripts\python.exe D:/pythonproject/私有属性2.py

=== 调用 __init__() 方法构造对象 ===

##################################################

调用__del__() 销毁对象,(对象占用的内存被回收)

**************************************************

Process finished with exit code 0

通过以上三个实例对比,我们不难发现:实例对象被引用了n次,计数器就为n,执行一次del 对象的引用那么所引用的这个实例对象的计数器就会自动减1,当实例对象的计数器减为零时,就会调用并且执行类中的__del__()方法,计数器不为零,则不会执行实例对象中的__del__()方法,那么就会等程序即将结束之前,python解释器会自动执行__del__()方法,销毁对象。

你可能感兴趣的:(python中的__del__()方法)