第10章不再纠结if 和case
前面我们说过,Verilog HDL和C语言很类似,学过C语言的都知道if和switch语句,它们在C语言编程中很常见。在Verilog HDL中,if和case条件语句同样是编程中的常客,他们与C语言很类似,但也存在差异。接下来这一章就来叨叨这两类条件语句,让大家不再纠结if和case。
10.1 if不同形态
if语句是条件语句的一种,所谓条件,就是语句的执行与否是有条件的,所以if语句主要有两部分组成,一是条件(也就是if后面的表达式),另一个就是满足条件时要执行的语句。Verilog HDL语言中的if语句主要有三种形式:
1) 形式1
if(条件)语句;
比如:if(a==b)
cout=0;
2) 形式2
if(条件)语句1;
else 语句2;
比如:if(a==b)
cout=0;
else
cout=1;
3) 形式3
If(条件1) 语句1;
else if(条件1)语句2;
…
else if(条件n-1) 语句n-1;
else 语句n;
比如:if(a==b)
cout=0;
else if(a>b)
cout=1;
else
cout=2;
上面我们说了if语句的三种形式,接下来说下if语句中需要注意的几点:
1)if中的条件表达式一般为关系表达式或者逻辑表达式。关系表达式就是用关系运算符(>,<,==等)将两个表达式连接起来的式子,逻辑表达式就是将关系表达式或逻辑量进行逻辑运算(与,或,非等)的式子。Verilog HDL在表达式的值只有0,1,x,z四种,若为“1”则“真”处理,执行指定的语句;若为“0,x,z”则按“假”处理,调过指定的语句。
2)else子句不能单独使用,出现else,必定有if与其配对,也就是有else的地方必须有if,有if的地方不一定有else。
3)在if的三种形式中的语句部分可以是复合型语句(begin_end语句块),也可以嵌套if语句。
如(begin_end语句块):
if(a>b)
begin
c<=0;
d<=0;
end
else
begin
c<=1;
d<=1;
end
又如(if的嵌套):
If(a>=b)
if(a==b) c<=0;
else c<=1;
else c<=2;
需要注意的if语句嵌套中,else总是和它上面最近的if配对。为了提高编程代码的可读性和可靠性,我们会用begin_end标明其作用区域。
比如:if(a>=b)
begin
if(a==b) c<=0;
end
else c<=2;
上例中如果不加begin_end,else就会与第二个来配对,这样的话它是与第一个if配对。
10.2 case不同形态
case语句是一种分支选择语句,他可以直接处理多分支选择。case语句有三种形式:
1)case(控制表达式) endcase
2)casez(控制表达式) endcase
3)case-x(控制表达式) endcase
case分支项的一般形式为:
常量表达式:语句;
…
default:语句;
case形式的用法:
1.case语句的必须关键字是case(casez,case-x)和endcase,它们是成双成对的,在书写代码的时候一定要记得写完case(casez,case-x)就要写endcase,在这种情况下,我们就不会因为忘记endcase关键字而出现语法错误(这种错误通常会有连锁反应),切记切记!
2.default项可以省略,但是一个case只能有一个default的项。
3.case语句只有控制表达式的值与常量表达式的值进行比较后全为1时才执行指定的语句。这样就要求控制表达式的值与常量表达式的位宽相等。
每一位相比较的结果,不同的形式可能会不同。三种形式case语句的真值表如下:
case形式的真值表
Case |
0 |
1 |
X |
z |
0 |
1 |
0 |
0 |
0 |
1 |
0 |
1 |
0 |
0 |
X |
0 |
0 |
1 |
0 |
Z |
0 |
0 |
0 |
1 |
casez形式的真值表
Casez |
0 |
1 |
X |
z |
0 |
1 |
0 |
0 |
1 |
1 |
0 |
1 |
0 |
1 |
X |
0 |
0 |
1 |
1 |
Z |
1 |
1 |
1 |
1 |
case-x形式的真值表
Case-x |
0 |
1 |
X |
z |
0 |
1 |
0 |
1 |
1 |
1 |
0 |
1 |
1 |
1 |
X |
1 |
1 |
1 |
1 |
Z |
1 |
1 |
1 |
1 |
从上面的真值可以看出,case形式必须完全相等时才为;casez则看重高阻态z,即对应位比较时,当有一个为z,另一个不管是什么值,结果都为真;case-x则看重高阻态z和不定值x,即对应位比较时,当有一个为z或x,另一个不管是什么值,结果都为真。casez和case-x形式可以用于带有优先级的编码或译码。
例子:
input [2:0] sel;
output reg [2:0] out;
case-x(sel)
3’b1xx: out<=1;
3’b01x: out<=2;
3’b001: out<=3;
default: out<=0;
endcase
上面例子优先比较高位,是带有优先级的译码器。
文章评论(0条评论)
登录后参与讨论