赋值
赋值没有产生新的存储空间,因为new仅执行了一次,赋值行为只是把地址入口传入另一个句柄,两个句柄指向的是同一个对象。 与$cast()相似
class assignment;
packet p1;
p1=new;
packet p2;
p2=p1;
endclass
复制(浅拷贝)
复制执行了两次new操作,产生了新的存储空间,且原存储空间所存的属性也被复制了过去。
calss shallow_copy;
packet p1;
p1=new;
packet p2;
p2=new p1;
endclass
但该复制行为属于浅复制,因为它只能复制源对象内部的属性,源对象内部的嵌套的对象属性并不会被复制。示例:
class A;
integer j=5;
endclass
class B;
integer i=1
A a=new; //在B类中例化了A类属性变量a
endclass
module shallow_copy();
Initial begin
B b1=new;
B b2=new b1; //b2是b1的一个再复制,b2中也有变量i和对象a
b1.i=10;
b1.a.j=50;
test=b2.i; //b2中的i不随b1中的i的改变而改变(b2.i=1)
test=b2.a.j; //由于复制仅复制了对象a的句柄,并没有为对象a开辟新的存储空间,也就是并没有复制对象a,因此,b2中的对象a和b1中的对象a是同一个对象,b1和b2共享同一个对象,所以b2.a.j=50
end
endmodule
深拷贝
深度复制就是不仅要复制源对象的属性,其内部嵌套的对象属性也一并复制进来,这需要自己写copy函数。
class A;
integer j=5;
endclass
class B;
integer i=1
A a=new;
function copy(B in_b); //在B类中声明copy函数
this.i=in_b.i; //this关键字限定此处的i为类属性,而不是copy函数自变量
this.a.j=in_b.a.j;
endfunction
endclass
module deep_copy();
initial begin
B b1=new;
B b2=new; 分别为两个对象b1和b2开辟存储空间,这样对象b1和b2都
b2.copy(b1); 各自独立的对象a,再利用copy函数,将b1的值赋给b2。
end
endmodule
克隆
克隆=构造+复制
在SystemVerilog中,类变量的赋值或$cast只会将句柄复制到对象,而不是对象本身。 大多数情况下,我们创建一个对象,分配或随机化该对象中的值,然后传递句柄。 但有时我们想修改对象的本地副本,所以我们将其克隆(构造+复制=克隆)。