SystemVerilog学习笔记(六)

是一种可以包含数据和方法(function,task)的类型。
例如一个数据包,可能被定义为一个类,类中可以包含指令、地址、队列ID、时间戳和数据等成员。

类的三要素:封装、继承、多态

OOP(面向对象编程)术语
类(class) : 包含成员变量和成员方法。
对象(object)
:类在例化后的实例。
句柄(handle) :指向对象的指针。
原型(prototype) :程序的声明部分,包含程序名、返回类型和参数列表。

1. 类、模块、结构体比较

c1、c2称为句柄(类似于c中的指针),句柄是否例化通过是否有new的动作判断。new是在仿真时让仿真器创建一个相应实例(如果没有定义new函数,系统也会自动添加一个function new)。调用new函数后,开辟空间存放存放变量。new函数没有返回值,无需表明返回值类型,甚至无需声明void。当创建了一个实际对象时,new函数的返回值为对象的头部句柄(指针)

仿真目的是仿真真实的硬件,没有run任何时间单位前,整个硬件的结构就确定下来了。在仿真前,模块是有值的,而对象的创建是在仿真以后才会执行:

仿真run 0(很小的时间单位)后:

同样地在进行仿真前,结构体也会有值(initial中的结构体静态变量同样如此),可进行如下验证:

在仿真开始前:

对new函数函数赋初值(new函数可以传参数)
对packet_c创建100个实例如下:

c1最终指向最后一个实例,前面99个实例无法找回。

总结:

  1. SV并不像C++语言一样要求复杂的存储空间开辟和销毁的手段,而是采用了像Java—样空间自动开辟和回收的手段。
  2. 因此SV的类在定义时,只需要定义构建函数(constructor)而不需要定义析构函数(destructor) 。
  3. 类在定义时,需要定义构建函数,如果未定义,则系统会自动帮助定义一个空的构建函数(没有形式参数,函数体亦为空)。

2. 句柄的拷贝

两个句柄一个对象,几个new几个对象。(赋值的是句柄,不是对象!)

3. 静态变量&动态变量

静态变量:仿真开始前已经分配空间
动态变量:仿真开始时才分配空间
默认类里面所有成员(成员变量、成员方法或者其他)均是动态的,如果想要使用静态的,可用static

此时句柄悬空,能否找到data?

编译器在编译时分析,句柄指向data是一个静态变量,仿真时data不会存放到任何实例化对象里面(c1.data、c2.data,任何一个data变量的存放空间不会在任何一个实例化的对象里面,如果存放在实例化对象里面,则空间各自独立。真正的空间在编译过程中开辟,可以姑且理解为放在类的下面)因此,编译器在编译时告诉我们说c1句柄指向的是packet这个类,data是一个静态变量。接下来仿真过程中找data时,不管c1有无指向对象,真正要找的变量放在类的域里面。

总结:

  1. 类的成员(变量/方法)默认都是动态(automatic)生命周期,即每一个对象的变量和方法都会为其开辟新的空间。
  2. 如果多个对象为了共享一个成员(变量/方法),那么可以为其添加关键字static。
  3. 多个对象因此可以共享同一个成员变量或者方法。
  4. 访问该成员时,无需进行对象的例化。
  5. 成员方法也可以声明为静态。
  6. 静态方法无法访问非静态成员(变量/方法),否则会发生编译错误。

4. this

  1. this是用来明确索引当前所在对象的成员(变量/参数/方法。
  2. this只可以用来在类的非静态成员、约束和覆盖组中使用。
  3. this的使用可以明确所指向变量的作用域。
    class Demo ;
    integer x;
    function new (integer x) ;
        this.x =x;
    endfunction
    endclass

    this
    赋值拷贝
    链表

    5.浅拷贝与深拷贝

    浅拷贝:只能拷贝成员里面的变量
    深拷贝:递进式拷贝,拷贝句柄及其指定对象。深拷贝与浅拷贝空间独立。

6. 数据的隐藏和封装

  1. 类的成员(变量/方法)默认情况下,即是公共属性的。这表示对于类自身和外部均可以访问该成员。
  2. 对于成员的限定,如果使用local,则只有该类可以访问此成员,而子类或者外部均无法访问。
  3. 对于成员的限定,如果使用protected,则表示该类和其子类均可以访问此成员,而外部无法访问。
    class Packet;
    local integer i ;
    function integer compare (Packet other) ;
        compare = (this.i =other.i) ;
    endfunction
    endclass
  4. 对于商业开发,类的提供方会限制一些类成员的外部访问权限,继而隐藏类成员的更多细节。这种方式也使得类的外部访问接口更为精简,减轻了类的维护工作量,也使得类在修改时便于与旧版本保持兼容。数据隐藏的方式使得类的测试和维护都变得更为简单。

7. 问答题

1.类和结构体的联系和差别有哪些?类和模块(module)的联系和差别有哪些?
类与结构体:
同:都可以包含指令、地址、队列ID、时间戳和数据等成员。
异:(1)类需要调用new函数进行例化,才会开辟空间存放存放变量。而结构体在仿真前就开辟空间存放变量;(2)类可以包含数据和方法(function,task)的类型。
类与模块:
同:都可以包含数据和方法(function,task)的类型。
异:(1)类中的成员变量和方法默认是动态的,而模块默认是静态的;(2)在仿真前,模块是有值的,而类中对象的创建是在仿真以后才会执行

3.如果有同名的模块,那么在编译过程中应该怎么解决“同名”问题?
可以用 this来明确索引当前所在对象的成员(变量/参数)方法。this只可以用来在类的非静态成员、约束和覆盖组中使用。

class Demo ;
    integer x;
    function new (integer x) ;
        this.x =x;
    endfunction
    endclass

可参考:结构体、模块和类的联系和区别? 类的学习小结 – 知乎 (zhihu.com)

暂无评论

发送评论 编辑评论


				
|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇