1. 数组的声明(一维和多维)
一维数组
int a[15];
二维数组
int a[16][5];
当访问越界地址时,读出的数据会是默认值,4值逻辑,如logic会返回x,2值逻辑如bit会读出0,而wire在没有驱动的时候会输出Z(高阻态)
2. 定宽数组初始化
int a[5] = '{ 0,1,2,3,4}; // ' 加 花括号作为声明方式
int a[5];
a[0:1] = '{1,2};
a = '{1,2,3,4,5};
a = '{1,2,default:1}; //其余三个都为1
a = '{5{1}}; //5个值都为1
int a[2][4] = '{'{1,2,3,4},'{5,6,7,8}}; //这里的[2]是最高维
3. 数据遍历
操作数组最常见的方式是使用for和foreach循环
$size()返回定宽数组的长度。
for()中的索引变量需要手动进行声明。
foreach()中的索引变量不用手动声明,sv会自动声明,且在这foreach循环中有效。
initial
begin
bit [7:0] dst, src;
foreach(src[i])
begin
dst[i] = src[i];
end
end
initial
begin
int dst[2][4] = '{'{1,2,3,4},'{4,5,6,7}};
foreach(dst[i,j])
begin
$display("dst[%0d][%0d] = %0d",i,j,dst[i][j]);
end
end
注意在多维数组使用foreach进行遍历时,使用的是foreach(数组[i,j]),并不是数组[i][j]。
4. 数组的比较只能限于等于比较或者不等于比较。
使用==进行判断
5. SV支持同时使用数组下标和位下标。
bit [7:0] a[5] = '{5{5}};//表示5个8bit,[5]为高维度
a[0] // 第一个元素数值5
a[0][0] //1 第一个元素的bit0位
a[1][2:0] //5 第二个元素的低3bit。
6. 合并数组和非合并数组
仿真器通常使用字边界来存放数据(4个字节),那么非合并数组byte/shortint/int会使用一个字存放,并且只使用低位的存储空间,高位空间都浪费了。
并且4值逻辑的存储会比2值逻辑多使用一倍存储空间。因为真值表的存储多一倍。
背景:对某些数据类型,希望既可以把它作为一个整体来访问,也可以把它分解成更小的单元。
Sv引入的合并数组就是它既可以作为数组,也可以单独作为数据。存放时连续排放,中间不会有任何闲置空间。
非合并数组
logic [4:0] a[8];//8个5bit元素
合并数组
logic [7:0] [4:0] a; 8个5Bit的数组a,[7:0]为高维度 [4:0]为低维度
声明规则:1. 维度在类型的后面第一个,第二个是一个数据的宽度,也就是8个5bit的数据。2.声明时维度使用[msb:lsb],绝对不能使用[size]。
合并数组间进行复制,即使数组维度不同也可以进行复制。因为操作是以bit为单位进行的。
合并数组和非合并数组可以混合使用
bit [3:0][7:0] a[5];
5表示非合并数数组部分
[3:0][7:0]表示合并部分
a[0] :第一层代表非合并数据,获取一个字(32位)
a[0][1] :第二层代表获取合并数组部分,获取一个字节
a[0][1][2]:获取一个bit位的数据。