复制对象
两种复制行为
存在两种基本的 MATLAB® 对象 - 句柄和值。
在复制操作方面,值对象的行为与 MATLAB 基础类型类似。副本是独立值。您对一个对象执行的操作不会影响该对象的副本。
句柄对象通过其句柄变量进行引用。句柄变量的副本引用同一个对象。您对句柄对象执行的操作对引用该对象的所有句柄变量可见。
句柄对象复制
如果您要定义类并想支持句柄对象复制,请参阅Implement Copy for Handle Classes。
值对象复制行为
MATLAB 数值变量属于值对象。例如,您将 a
复制为变量 b
时,这两个变量彼此独立。更改 a
的值并不会更改 b
的值:
a = 8; b = a;
现在重新为 a
赋值,而 b
不变:
a = 6; b
b = 8
清除 a
不会影响 b
:
clear a
b
b = 8
值对象属性
作为值对象中的属性存储的值的复制行为与数值变量相同。例如,假定 vobj1
是带有属性 a
的值对象:
vobj1.a = 8;
如果您将 vobj1
复制到 vobj2
,然后更改 vobj1
属性 a
的值,则复制对象的属性 vobj2.a
的值将保持不变:
vobj2 =vobj1; vobj1.a = 5; vobj2.a
ans = 8
句柄对象复制行为
此处提供的句柄类称为 HdClass
,它定义称为 Data
的属性。
classdef HdClass < handle properties Data end methods function obj = HdClass(val) if nargin > 0 obj.Data = val; end end end end
创建此类的对象:
hobj1 = HdClass(8)
由于该语句不是通过分号终止的,因此 MATLAB 显示有关该对象的信息:
hobj1 = HdClass with properties: Data: 8
变量 hobj1
是引用所创建对象的句柄。将 hobj1
复制到 hobj2
会生成引用同一对象的另一个句柄:
hobj2 = hobj1
hobj2 = HdClass with properties: Data: 8
由于句柄引用该对象,复制句柄会将句柄复制为一个新的变量名称,但该句柄仍然引用同一对象。例如,假定 hobj1
是带有属性 Data
的句柄对象:
hobj1.Data
ans = 8
更改 hobj1
的 Data
属性的值,则所复制对象的 Data
属性值也会随之更改:
hobj1.Data = 5; hobj2.Data
ans = 5
由于 hobj2
和 hobj1
是同一对象的句柄,更改副本 hobj2
还会更改您通过句柄 hobj1
访问的数据:
hobj2.Data = 17; hobj1.Data
ans = 17
为句柄变量重新赋值
为句柄变量重新赋值会生成与为任何 MATLAB 变量重新赋值相同的结果。创建一个对象并将其赋给 hobj1
时:
hobj1 = HdClass(3.14);
hobj1
引用新对象,而不是以前引用的同一对象(并且仍是由 hobj2
引用)。
清除句柄变量
从工作区中清除句柄时,MATLAB 会删除变量,但不会删除另一个句柄引用的对象。但是,如果没有指向对象的引用,则 MATLAB 会销毁该对象。
假定 hobj1
和 hobj2
都引用同一对象,您可以清除其中任一句柄而不会影响该对象:
hobj1.Data = 2^8; clear hobj1 hobj2
hobj2 = HdClass with properties: Data: 256
如果您同时清除 hobj1
和 hobj2
,则将不存在指向该对象的引用。MATLAB 将销毁该对象并释放该对象使用的内存。
删除句柄对象
要删除由任意数量的句柄引用的对象,请使用 delete
。假定 hobj1
和 hobj2
都引用同一对象,请删除其中任一句柄。MATLAB 会删除该对象:
hobj1 = HdClass(8); hobj2 = hobj1; delete(hobj1) hobj2
hobj2 = handle to deleted HdClass
使用 clear
从工作区中删除变量。
修改对象
将对象传递给函数时,MATLAB 会将该对象的副本传递到函数工作区。如果该函数修改了对象,MATLAB 将仅修改函数工作区中对象的副本。句柄与值类之间的复制行为的区别在以下情况中很重要:
值对象 - 函数必须返回对象的已修改副本。要在调用方工作区中修改该对象,请将函数输出分配具有相同名称的变量
句柄对象 - 函数工作区中的副本引用同一个对象。因此,该函数无需返回已修改的副本。
测试句柄或值类
要确定对象是否为句柄对象,请使用 isa
函数。如果 obj
为某个类的对象,则此语句将确定 obj
是否为句柄:
isa(obj,'handle')
例如,containers.Map
类创建句柄对象:
hobj = containers.Map({'Red Sox','Yankees'},{'Boston','New York'}); isa(hobj,'handle')
ans = 1
hobj
还是 containers.Map
对象:
isa(hobj,'containers.Map')
ans = 1
查询 hobj
的类会显示它是 containers.Map
对象:
class(hobj)
ans = containers.Map
class
函数会返回特定类的对象。