首页 文章

两个补充 - 如何处理负数?

提问于
浏览
1

我的理解是使用两个人的赞美来否定数字,我的理解是:!num 1.所以我的问题是这是否意味着,对于变量'foo'= 1,否定'foo'将是正确的与变量'bar'相同= 255 . 如果我们要检查-'foo'=='bar'或if -'foo'== 255,我们会得到它们是平等的吗?我知道有些语言,比如Java,会保留一个符号 - 因此比较会产生错误 . 什么语言不?我假设汇编程序/本机没有符号位 .

除了所有这些之外,我还读到了一个零标志或一个结转标志,当一个'负数'被添加到另一个(任何符号)号码时设置 . 由于二进制补码的工作方式,0x01 0xff = 0x00(前导1被截断),无论何时添加该标志都会被置位 . 这个标志究竟用于什么?

我的最后一个问题,对于其他数学运算(例如乘法),我是否必须重新否定数字(现在它是正数),执行运算,否定结果?例如,!((!neg 1)* pos)1 .

编辑完成了问题,所以请随意消防 .

1 回答

  • 2

    是的,在二进制补码中,数字x表示为~x 1,其中~x是某些固定数字位的x的二进制数的按位补码 . 例如,对于8位,x的二进制数字是000000001,因此按位补码是11111110,并且加1产生11111111 .

    没有办法在8位二进制(没有符号)中区分八位二进制补码中的-1和255 . 它们在位中具有相同的表示形式:11111111 . 如果使用这两个数字,则必须单独记住哪一个是8位二进制补码,哪一个是纯八位二进制,或者必须使用多于8位 . 换句话说,在原始位级别,11111111只是8位;在我们决定如何解释之前,它没有任何 Value .

    Java和典型的其他语言不保持与数字值分开的符号位;该符号是数字编码的一部分 . 此外,典型语言不允许您比较不同类型 . 如果你有一个二进制补码x和一个无符号y,那么在比较之前必须将其中一个转换为另一个的类型,或者它们必须都转换为第三种类型 . 因此,如果比较x和y,并将一个转换为另一个,那么转换将溢出或换行,并且您不能期望得到正确的数学结果 . 为了比较这两个数字,我们可能将它们中的每一个转换为更宽的整数,例如32位,然后进行比较 . 将8位二进制补码11111111转换为32位整数会产生-1,将8位纯二进制11111111转换为32位整数会产生255,然后比较报告它们是不相等的 .

    您读取的零标志和进位标志是在计算机处理器中执行比较指令时设置的标志 . 大多数高级语言都不允许您直接访问这些标志 . 许多处理器都有一个如下形式的指令:

    cmp a, b
    

    该指令从a中减去b并丢弃差值,但会记住描述减法的几个标志:结果为零(零标志)?借款是否发生(借旗)?结果是否定的(标志旗)?是否发生溢出(溢出标志)?

    比较指令要求被比较的两个事物是相同的类型(二进制补码或无符号),但它不关心哪种类型 . 稍后可以通过根据类型检查标志的特定组合来测试结果 . 也就是说,根据所进行的测试,记录在标志中的信息可以区分一个二进制补码是否大于另一个,或者一个无符号数是否大于另一个 . 有条件分支指令可以测试所需的标志属性 .

    通常不需要“取消否定”数字来执行算术运算 . 处理器包括处理二进制补码的算术指令 . 通常,加法和减法指令是类型无关的,与比较指令的方式相同,但乘法和除法指令不是(除了某些形式的乘法返回部分结果) . 加法和减法指令可以是类型不可知的,因为算术中发生的包装适用于二进制补码和无符号 . 但是,包装不适用于乘法和除法 .

相关问题