当前位置: 首页 > news >正文

C语言中整数编码方式(原码、反码、补码)

在 C 语言中,原码、反码、补码的运算规则与其编码特性密切相关,核心差异体现在符号位是否参与运算、进位如何处理以及减法是否能转化为加法等方面。以下是三者的运算规则及特点分析(以 8 位整数为例,符号位为最高位):

一、原码的运算规则

原码是 “符号位 + 数值绝对值” 的直接表示,其运算规则需单独处理符号位,且加法和减法需分开逻辑,灵活性差。

1. 加法运算
  • 若两数符号相同(同正或同负):

符号位不变(仍为 0 或 1),数值位直接相加;若数值位相加后有进位,结果可能溢出(超出表示范围)。

示例:+3(00000011) + +5(00000101)

符号位均为 0,数值位相加:0000101 + 000011 = 0001000,结果为00001000(+8,正确)。

  • 若两数符号不同(一正一负):

需先比较两数数值位的绝对值大小,用 “大绝对值 - 小绝对值”,结果的符号取 “绝对值大的数” 的符号。

示例:+5(00000101) + (-3)(10000011)

绝对值 5 > 3,符号取正(0),数值位相减:0000101 - 0000011 = 0000010,结果为00000010(+2,正确)。

2. 减法运算

原码减法需转化为 “被减数 + 减数的相反数”,再按加法规则处理(符号相反时的加法逻辑)。

示例:+5(00000101) - (+3)(00000011)

等价于 +5 + (-3),按符号不同的加法规则计算,结果为 + 2(正确)。

原码运算的缺陷
  • 符号位需单独判断,运算逻辑复杂(需比较绝对值、区分加减);
  • 存在两个 0(+0 和 - 0),可能导致运算结果歧义;
  • 实际中几乎不用于计算机运算(仅用于直观表示)。

二、反码的运算规则

反码是原码到补码的过渡编码,其运算规则允许符号位参与运算,但需处理 “循环进位”(最高位进位需回加到最低位),可实现减法转加法,但仍有缺陷。

1. 加法运算
  • 符号位与数值位一起参与加法(按二进制加法规则,逢 2 进 1);
  • 若最高位(符号位)产生进位,需将该进位 “循环” 加到结果的最低位(称为 “循环进位”);
  • 运算结果仍为反码,需转换为原码才能得到实际值。

示例 1:+3(反码00000011) + +5(反码00000101)

直接相加:00000011 + 00000101 = 00001000(无进位),结果反码为 00001000,对应原码 + 8(正确)。

示例 2:+5(反码00000101) + (-3)(反码11111100)

相加:00000101 + 11111100 = 100000001(最高位产生进位 1);

循环进位:将进位 1 加到最低位,00000001 + 1 = 00000010;

结果反码为 00000010,对应原码 + 2(正确)。

示例 3:+1(反码00000001) + (-1)(反码11111110)

相加:00000001 + 11111110 = 11111111(无进位);

结果反码为 11111111,对应原码 - 0(存在双 0 问题,不完美)。

2. 减法运算

反码减法可直接转化为 “被减数 + 减数的反码”(因负数的反码是其相反数的反码),再按加法规则处理(含循环进位)。

示例:+5 - (+3) 等价于 +5 + (-3),同上述示例 2,结果正确。

反码运算的缺陷
  • 需处理循环进位,硬件实现稍复杂;
  • 仍存在 - 0(11111111),导致 0 的表示不唯一;
  • 未彻底解决运算问题,仅作为补码的过渡。

三、补码的运算规则

补码是计算机中实际使用的编码,其运算规则最简单:符号位直接参与运算,进位直接丢弃,减法可完美转化为加法,且结果唯一正确。

1. 加法运算
  • 符号位与数值位一起参与加法(按二进制加法规则,逢 2 进 1);
  • 若最高位(符号位)产生进位,直接丢弃该进位(因超出位数的部分不影响结果);
  • 运算结果仍为补码,无需额外处理即可表示正确值。

示例 1:+3(补码00000011) + +5(补码00000101)

相加:00000011 + 00000101 = 00001000(无进位),结果补码为 00001000,对应 + 8(正确)。

示例 2:+5(补码00000101) + (-3)(补码11111101)

相加:00000101 + 11111101 = 100000010(最高位产生进位 1);

丢弃进位:结果为 00000010,对应 + 2(正确)。

示例 3:+1(补码00000001) + (-1)(补码11111111)

相加:00000001 + 11111111 = 100000000(进位 1);

丢弃进位:结果为 00000000(唯一的 0,正确)。

2. 减法运算

补码减法可直接转化为 “被减数 + 减数的补码”(因减去一个数 = 加上它的相反数,而负数的补码是其相反数的补码),再按加法规则处理(进位丢弃)。

公式:a - b = a + (-b)的补码

示例:+5 - (+3) = +5 + (-3)的补码

-3 的补码为 11111101,相加结果同示例 2,得 + 2(正确)。

补码运算的优势
  • 符号位自然参与运算,无需单独判断;
  • 减法完全转化为加法,简化硬件设计(只需加法器);
  • 只有一个 0(00000000),结果无歧义;
  • 进位直接丢弃,逻辑简单,是计算机中整数运算的唯一实现方式。

四、无符号数的运算规则

无符号数(unsigned)没有符号位,其原码、反码、补码完全相同(即二进制数值本身),运算规则为:

  • 加法:按二进制加法,进位直接丢弃(超出位数的部分无效);
  • 减法:按二进制减法,若被减数小于减数,结果为 “模” 减去(减数 - 被减数)(等价于补码运算,因无符号数的补码即自身)。

示例(8 位无符号数):5 - 10

等价于 5 + (256 - 10) = 5 + 246 = 251(因 8 位无符号数的模为 256),结果为 251(正确,无符号数减法的 “借位” 通过模运算处理)。

总结

编码

加法规则

减法规则

核心特点

原码

符号位单独处理,异号需比较绝对值

转化为 “被减数 + 相反数”,同加法

逻辑复杂,有双 0,几乎不用

反码

符号位参与运算,进位循环到最低位

转化为 “被减数 + 减数的反码”

需循环进位,仍有 - 0,过渡编码

补码

符号位参与运算,进位直接丢弃

转化为 “被减数 + 减数的补码”

逻辑简单,无歧义,计算机实际使用

补码的运算规则是 C 语言中整数存储和运算的基础,理解其规则可解释负数运算、溢出(如int a = 127 + 1结果为 - 128)等现象。

http://www.dtcms.com/a/275848.html

相关文章:

  • C++ 模板工厂、支持任意参数代理、模板元编程
  • 如何使用postman做接口测试?
  • dify 用postman调试参数注意
  • MOSFET驱动电路设计时,为什么“慢”开,“快”关?
  • 《Java Web程序设计》实验报告二 学习使用HTML标签、表格、表单
  • 零基础搭建监控系统:Grafana+InfluxDB 保姆级教程,5分钟可视化服务器性能!​
  • elementuiPlus+vue3手脚架后台管理系统,上生产环境之后,如何隐藏vite.config.ts的target地址
  • 游戏开发日记7.12
  • 现代C++打造音乐推荐系统:看看如何从0到1实现
  • 80. 删除有序数组中的重复项 II
  • Web学习笔记3
  • 网络检测:Linux下实时获取WiFi与热点状态
  • 游戏开发团队并非蚂蚁协作(随记):在各种“外部攻击”下保护自己的工具
  • C++中的容斥原理
  • css 判断是ios设备 是Safari浏览器
  • 敏捷开发方法全景解析
  • vue2和vue3的响应式原理
  • 【Datawhale AI 夏令营】 用AI做带货视频评论分析(二)
  • npgsql/dapper/postgresql的时区问题
  • 深入解析 LinkedList
  • Windows去除管理员弹窗确认
  • Claude code在Windows上的配置流程
  • 【6.1.0 漫画数据库技术选型】
  • Linux系统中安装mysql详解
  • 计算机毕业设计springboot扶贫助农与产品合作系统 基于SpringBoot的农村电商助农平台设计与实现 乡村振兴背景下的农产品对接与帮扶管理系统
  • C语言课程设计--电子万年历
  • 【数据分析】03 - Matplotlib
  • 9.2 埃尔米特矩阵和酉矩阵
  • Go内存分配
  • linux系统mysql性能优化