在本教程中,我们将学习如何使用Python脚本创建浅拷贝和深拷贝。通常,我们使用赋值操作符(=)来创建Python对象的副本。让我们了解与在Python中创建副本相关的全部概念。

Python中的拷贝

众所周知,赋值操作符用于创建Python对象的副本,但这并不正确;它只是创建目标和对象之间的绑定。当我们使用赋值操作符时,它不会创建一个新对象,而是创建一个新变量,该变量与旧对象的引用共享。

拷贝在用户想要在不同时修改原始对象的情况下很有用。用户还喜欢创建副本以处理可变对象。

让我们理解以下示例。

示例 -

list1 = [[1, 2, 3], [4, 5, 6], [7, 8, 'a']]  
list2 = list1  
  
list2[1][2] = 4  
  
print('Old List:', list1)  
print('ID of Old List:', id(list1))  
  
print('New List:', list2)  
print('ID of New List:', id(list2)) 

输出:

Old List: [[1, 2, 3], [4, 5, 4], [7, 8, 'a']]
ID of Old List: 1909447368968
New List: [[1, 2, 3], [4, 5, 4], [7, 8, 'a']]
ID of New List: 1909447368968

解释:

在上面的输出中,我们可以看到变量list1list2共享相同的ID 1909447368968。

如果我们在list1list2中做任何更改,更改将反映在两者中。

Python中的拷贝类型

主要目的是创建Python对象的副本,以便我们可以修改副本而不更改原始数据。在Python中,有两种方法可以创建副本。

  • 浅拷贝
  • 深拷贝

我们将使用copy模块来创建上述副本。

copy 模块

copy模块用于创建浅拷贝和深拷贝。让我们看看每种方法。

浅拷贝

浅拷贝是对象的副本,它存储原始元素的引用。它创建新的集合对象,然后将其填充为对原始对象中找到的子对象的引用。

它复制嵌套对象的引用,而不会创建嵌套对象的副本。因此,如果我们对对象的副本进行任何更改,这些更改将反映在原始对象中。我们将使用copy()函数来实现它。

示例 -

# importing "copy" for copy operations   
import copy   
  
# initializing list 1   
list1 = [1, 7, [3,5], 8]   
  
# using copy to shallow copy   
list2 = copy.copy(list1)   
  
# original elements of list   
print ("The original elements before shallow copying")   
for i in range(0,len(list1)):   
   print (list1[i],end=" ")   
  
print("\r")   
  
# adding and element to new list   
list2[2][0] = 10  
  
# checking if change is reflected   
print ("The original elements after shallow copying")   
for i in range(0,len( list1)):   
   print (list1[i],end=" ") 

输出:

The original elements before shallow copying
1 7 [3, 5] 8 
The original elements after shallow copying
1 7 [10, 5] 8

在上面的代码中,我们对list1进行了更改,这种更改反映在另一个列表中。

示例 - 2

import copy  
  
list1 = [[1, 2, 3], [4, 5, 6], [7, 8, 9], [10, 11, 12]]  
list2 = copy.copy(list1)  
  
list1.append([13, 14,15])  
  
print("Old list:", list1)  
print("New list:", list2)

输出:

Old list: [[1, 2, 3], [4, 5, 6], [7, 8, 9], [10, 11, 12], [13, 14, 15]]
New list: [[1, 2, 3], [4, 5, 6], [7, 8, 9], [10, 11, 12]]

解释:

在上面的代码中,我们创建了list1的浅拷贝。新创建的list2包含原始list1中存储的嵌套对象的引用。然后,我们将[13, 14, 15]附加到旧列表中,但子列表没有复制到新列表中。

Python 中的深拷贝

深拷贝是一个过程,我们在其中创建一个新对象并递归添加副本元素。我们将使用copy模块中提供的deepcopy()方法。独立的副本是原始对象及其整个对象的副本。让我们理解以下示例。

示例 -

import copy  
x = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]  
z = copy.deepcopy(xs)  
print(x)  
prin(z)

输出:

[[1, 2, 3], [4, 5, 6], [7, 8, 9]]
[[1, 2, 3], [4, 5, 6], [7, 8, 9]]

解释 -

在上述输出中,我们可以看到 z 是通过使用 deepcopy() 方法创建的 x 的克隆。如果我们更改其中一个子元素,不会影响原始对象。

深拷贝中两个对象是完全独立的。列表 x 被递归克隆,包括其所有子对象。

import copy  
x = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]  
z = copy.deepcopy(x)  
  
x[2][2] = 'Hello'  
print(x)  

示例 - 2:

import copy   
  
list1 = [0, [1, 2], [3,5], 4]   
  
# using deepcopy to deep copy   
list2 = copy.deepcopy(list1)   
  
# original elements of list   
print ("The original list: ")  
for i in range(0,len(list1)):   
   print (list1[i],end=" ")   
  
print("\r")   
  
# adding and element to new list   
list2[1][0] = 8  
  
# Change is reflected in l2   
print ("The new list after deep copying: ")  
for i in range(0,len( list1)):   
   print (list2[i],end=" ")   
  
print("\r")   
  
# Change is NOT reflected in original list   
# as it is a deep copy   
print ("The original elements:")  
for i in range(0,len( list1)):   
   print (list1[i],end=" ")   

输出:

The original list: 
0 [1, 2] [3, 5] 4 
The new list after deep copying: 
0 [8, 2] [3, 5] 4 
The original elements:
0 [1, 2] [3, 5] 4

拷贝任意Python对象

我们还可以使用拷贝方法来复制任意Python对象,包括自定义类。copy.copy()copy.deepcopy() 方法可以用于复制任何对象。

让我们了解以下示例。

示例 -

import copy  
class Func_New:  
    def __init__(self, x, y):  
        self.x = x  
        self.y = y  
  
    def __repr__(self):  
      return 'Func_new(%r, %r)' % (self.x, self.y)  
  
a = Func_New(50, 56)  
b = copy.copy(a)  
  
print(a)  
print(b)  
  
print(a is b)  
print(b is a)  

输出:

Func_new(50, 56)
Func_new(50, 56)
False
False

解释 -

在上面的代码中,我们创建了一个名为 Func_new 的用户定义类,并定义了 repr() 方法来检查对象。接下来,我们使用拷贝模块创建了浅拷贝。我们实例化了这个类,并检查了原始对象和它的浅拷贝是否相同。

需要记住的要点

复合对象是浅拷贝和深拷贝之间的主要区别。包含其他对象的对象,例如列表或类实例,被称为列表或类实例。

  • 浅拷贝创建一个新的复合对象,然后添加一个对原始对象中找到的对象的引用。
  • 深拷贝创建一个新的复合对象,然后添加一个对原始对象中找到的对象的引用。
  • 我们可以使用拷贝模块复制任意对象(包括自定义类)。

标签: Tkinter教程, Tkinter安装, Tkinter库, Tkinter入门, Tkinter学习, Tkinter入门教程, Tkinter, Tkinter进阶, Tkinter指南, Tkinter学习指南, Tkinter进阶教程, Tkinter编程