FPGA有符号数相关运算

1.有符号数放大2^n次方倍

运用 算数左移符号 <<<,此时会将符号位填补在最低位上。

2.当需要将8位宽的有符号数b,赋值给16位宽的有符号数a时:

a = {{8{b[7]}},xin}; 即需要将符号位扩展。

3.无符号数相减成负数时是否会自动变成有符号数?

无符号相减时,无论结果变量是否定义为有符号数,结果的二进制数值是完全一样的,本文做了如下实验:

module test(
	input[7:0]	a,
	input[7:0]  b,

	output[7:0] a_b,
	output signed[7:0] a_b_signed

	);

assign a_b = a - b;
assign a_b_signed = a - b;

endmodule

当a b 取不同的值仿真结果如下:
在这里插入图片描述
由上图可知若都按16进制形式看数据,数值都是一致的。但当无符号数以无符号形式看,有符号数以有符号形式看时,结果不一致。
在这里插入图片描述
此处仅看无符号数结果,如下表:

aba_b_signed
2551-2
12552
12-1
725
由上表可知,若将无符数相减,若位宽不变,直接视为有符号数,结果产生溢出导致计算结果不正确。因此,若无符号数减法运算可能产生负数时,需要保证结果的位宽比被减数和减数位宽的最大值大一位宽。
加一位宽后仿真结果如下,当两个结果均以有符号形式看时
在这里插入图片描述
由上图可知,两种方式计算结果均正确。因此可得出结论:

1. 无符号数相减变有符号数时,首先需要保证结果的位宽比被减数和减数位宽的最大值大一位宽。
2. 结果变量是否有定义为signed对结果数据不会有影响。

4.$signed 注意事项

module test(
	input[7:0]	a,
	input[7:0]  b,

	output[8:0] a_b,
	output signed[8:0] a_b_singed

	);

assign a_b = a - b;
assign a_b_singed = $signed(a) - $signed(b);

endmodule

将无符号数转化为有符号数进行运算时,应当确保无符号数的最高位为0,若最高位不为零应当扩展一位0,否则会直接被视为负数进行运算。

5.有符号数赋值的特点

示例代码如下,(可直接运行的仿真代码)

`timescale 1ns / 1ps
module test();

reg signed[4:0] a_unsigned;
reg signed[8:0] b_signed;
reg signed[15:0] c_signed;
reg clk;

always #5 clk = ~clk;

initial begin
	clk = 0;
	b_signed = -9'd7;
	#50
	b_signed = -9'd100;
	#50
	b_signed = -9'd128;
	#50
	b_signed = 9'd100;
end

always @(posedge clk) begin
	a_unsigned <= b_signed;
	c_signed <= b_signed;
end

endmodule

仿真结果如下图所示:
在这里插入图片描述
因此可以得出结论:
1.当一个有符号数赋值给一个位宽更大的量时(无论结果量是否定义符号位),都会自动的在高位补充符号位;
2.当一个有符号数赋值给一个位宽更小的量时(无论结果量是否定义符号位),都只会截取低位的数据。

待续,,,

  • 4
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值