赞
踩
原码是最直观的表示方法,它将一个数的符号和大小分开表示。
在一个n位的二进制数中,最高位(最左边的位)用作符号位,0表示正数,1表示负数。
剩下的n-1位表示数值的大小(绝对值)。
例如,对于8位二进制数,+3的原码表示为00000011,而-3的原码表示为10000011。
反码是原码的一种变体,用于简化二进制加法运算。
对于非负数,反码与其原码相同。
对于负数,反码是将其原码中的所有位取反(0变1,1变0),但符号位保持不变。
例如,+3的反码仍然是00000011,而-3的反码是11111100。
补码是现代计算机系统中最常用的表示有符号数值的方法。
对于非负数,补码与其原码和反码相同。
对于负数,补码是将其反码加1。
补码的一个重要特性是它允许使用相同的加法硬件电路来执行减法。在补码系统中,两个数的加法结果如果溢出,那么它实际上是两个数的和减去2的n次方(n是位数)。
例如,+3的补码是00000011,而-3的补码是11111101(即11111100加1)。
补码的另一个特性是它消除了负零的概念,即-0的补码表示与0的补码表示相同。
在补码系统中,所有的算术运算(加、减、乘、除)都可以统一处理,这大大简化了计算机的硬件设计。此外,补码也使得比较操作更加直观,因为可以直接比较两个数的二进制表示,而不需要额外的逻辑来处理符号。
无符号数计算需要注意进位。
- reg [7:0] a = 127;
-
- reg [7:0] b = 127;
-
- reg [8:0] c;
-
- always@(posedge clk)
-
- c <= a + b;
有符号数计算需要注意复制符号位
- reg [7:0] a = -5;
-
- reg [7:0] b = -6;
-
- reg [8:0] c;
-
- always@(posedge clk)
-
- c <={a[7], a} + {b[7], b};
数据位宽:确保加法器的输入和输出数据位宽一致,以便正确执行加法运算。如果输入数据位宽不一致,需要进行位宽扩展或截断。
溢出处理:当加法运算的结果超出了数据位宽所能表示的范围时,会发生溢出。在设计加法器时,需要考虑如何处理溢出,例如使用符号扩展或饱和运算。
减法运算,实质是 a-b可转换为 a + b(补码)
2.2.1 简介
在Verilog中,signed
关键字用于指定变量的符号。在数字系统中,数据可以是有符号的(signed)或无符号的(unsigned)。有符号数据可以表示正数、负数和零,而无符号数据只能表示非负数(包括零)。
在Verilog中,如果你不指定signed
或unsigned
,那么默认情况下,所有的整数(integer)和reg类型的变量都是无符号的。当你需要处理有符号数时,你可以在声明变量时使用signed
关键字。例如:
- reg signed [7:0] a; // 8位有符号寄存器
- reg [7:0] b; // 8位无符号寄存器,默认
在这个例子中,a
是一个8位的有符号寄存器,它可以存储的值范围是从-128到127(因为8位二进制可以表示256个不同的值,其中128个用于表示负数,0到127用于表示正数)。而b
是一个8位的无符号寄存器,它可以存储的值范围是从0到255。
有符号数和无符号数不能混合运算,否则容易出错。
绝对值是一个数去掉符号位的值。在Verilog中,可以使用条件判断语句来实现绝对值的计算。对于一个二进制数,如果最高位(符号位)为1,则表示这个数是负数,我们需要将其取反并加1来得到绝对值。如果最高位为0,则表示这个数是非负数,直接使用原值即可。
以下是一个计算4位二进制数绝对值的Verilog代码示例:
- module absolute_value(
- input [3:0] a, // 输入信号
- output [3:0] abs_a // 输出绝对值
- );
-
- always @(*) begin
- if (a[3]) begin // 如果最高位为1,表示负数
- abs_a = ~a + 1; // 取反加1得到绝对值
- end else begin
- abs_a = a; // 如果最高位为0,直接使用原值
- end
- end
-
- endmodule
- module SignExtension(
- input wire clk, // 时钟信号
- input wire a_sign, // 符号位,1表示负数,0表示非负数
- input wire [6:0] a_abs, // 绝对值部分
- output reg [7:0] a // 输出的有符号数
- );
-
- // always块在时钟上升沿触发时执行
- always @(posedge clk) begin
- // 根据a_sign的值来决定是否进行二进制补码操作
- a <= a_sign ? (~{1'b0, a_abs} + 1) : {1'b0, a_abs};
- end
-
- endmodule
它将一个7位的无符号数a_abs和一个符号位a_sign扩展为一个8位的有符号数a。在时钟上升沿,模块会检查a_sign的值,如果为1,则将a_abs视为负数的绝对值,进行二进制补码运算得到a(此时为负数);如果为0,则直接将a_abs的最高位补0得到a。
浮点数是一种用于近似表示实数的数学表达方式,它在计算机科学和工程领域中广泛使用。浮点数的设计目的是为了在有限的数字精度下,能够表示非常大或非常小的数值,以及它们之间的比率。
浮点数通常由三个部分组成:符号位(Sign)、指数(Exponent)和尾数(Mantissa 或 Fraction)。
符号位:表示数值的正负。通常用一个位(bit)来表示,0代表正数,1代表负数。
指数:表示数值的范围或大小。它是一个二进制数,用于表示数值的指数部分。在科学计数法中,一个数可以表示为M × 2^E的形式,其中M是尾数,E是指数。在浮点数表示中,指数部分用于存储E的值,通常采用偏移量(bias)的方式来编码,以便于处理。
尾数(或小数部分):表示数值的精确度。它是数值的主体部分,通常以二进制小数的形式表示。在科学计数法中,它对应于M的部分
浮点数的表示遵循IEEE 754标准,这是一个国际标准,定义了浮点数的格式和计算规则。根据这个标准,最常见的浮点数格式有两种:
在浮点数的表示中,指数部分通常使用一种称为“二进制指数”(Binary Exponent)的格式。为了简化计算和存储,指数部分并不是直接存储为实际的数值,而是存储为一个经过编码的值,这就是所谓的“移码”。
移码的工作原理如下:
举个例子,假设我们有一个浮点数,其实际指数值为-3。如果我们使用的是单精度浮点数(32位),其偏移量通常是127。那么,这个指数值的移码就是 -3 + 127 = 124。这个124(二进制表示)就会被存储在浮点数的指数部分。当计算机需要这个指数值时,它会从124中减去127,得到-3。假设其指数部分为3,在移码表示中,我们需要将3加上偏移量127,得到130,然后将130转换为二进制表示,即10000010。这样,我们就得到了指数部分的移码表示。
定点数是一种在计算机系统中表示数值的方法,它将数值的整数部分和小数部分固定在特定的位数上。在定点数表示法中,数值被分为几个部分:符号位、指数位(或称为阶码位)和尾数位(或称为有效数字位)。这种表示法与浮点数表示法不同,浮点数允许小数点的位置在数值中动态变化。
固定小数点:在定点数表示法中,小数点的位置是固定的,这意味着数值的精度和范围是有限的。例如,一个8位的定点数可能由1位符号位、3位整数位和4位小数位组成。
简化计算:由于小数点位置固定,定点数的加、减、乘、除等运算相对简单,不需要像浮点数那样进行小数点的移动和舍入。
有限精度:定点数的精度受限于其位数。例如,一个8位的定点数可能无法精确表示大于1或小于0.125的数值。
应用场景:定点数常用于嵌入式系统、微控制器和其他资源受限的环境中,因为它们可以提供快速且资源消耗较低的数值计算。
定点数的表示形式通常有两种:
假设我们有一个8位的数字,我们可以将其分为两部分,5位用于整数部分,3位用于小数部分。例如:
二进制表示: 1 0 1 1 0 . 1 0 1
对应的十进制: 32 + 16 + 8 + 0.5 + 0.125 = 56.625
小数点左侧的每一位代表2的幂次,从右到左依次是2^0, 2^1, 2^2, 2^3, 2^4。小数点右侧每一位代表2的负幂次,从左到右依次是2^-1, 2^-3。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。