驻马店市网站建设_网站建设公司_Sketch_seo优化
2026/1/11 5:21:00 网站建设 项目流程

从零搭建8位加法器:用与或非门点亮第一个“进位波纹”

你有没有想过,一个简单的1 + 1 = 2在计算机底层是如何实现的?不是调用库函数,也不是靠CPU指令——而是由最基础的逻辑门一步步“推”出来的。今天我们就来干一件“原始”但极其硬核的事:只用与门(AND)、或门(OR)、非门(NOT),从头构建一个能完成两个8位二进制数相加的电路。

这不仅是数字电路课的经典实验,更是一次对计算本质的深度探索。当你亲手让八个全加器串联起来,看着进位信号像波纹一样从低位传到高位时,那种“原来如此”的顿悟感,是任何高级语言都给不了的。


全加器:一切算术的起点

所有复杂运算,归根结底都是加法。而加法的最小单元,就是全加器(Full Adder, FA)

它有三个输入:
- A 和 B:两个要相加的一位二进制数;
- Cin:来自更低一位的进位。

输出两个结果:
- S:本位的和;
- Cout:是否向更高一位产生进位。

比如当 A=1、B=1、Cin=0 时,结果是 S=0,Cout=1 —— 就像十进制里 5+5=10,个位归零,向十位进一。

不用异或门,也能实现异或?

很多教程直接写S = A ^ B ^ Cin,简洁明了。但在真实硬件中,如果你手头只有与、或、非三种门(比如你在用74HC系列搭电路),那就得想办法“造出”异或功能。

我们知道:
$$
A \oplus B = (\neg A \cdot B) + (A \cdot \neg B)
$$
扩展到三位异或虽然复杂些,但依然可以通过乘积项之和的方式表达。于是我们可以把Sum 输出看作四个最小项的或运算

条件对应逻辑表达式
A=0, B=0, Cin=1¬A · ¬B · Cin
A=0, B=1, Cin=0¬A · B · ¬Cin
A=1, B=0, Cin=0A · ¬B · ¬Cin
A=1, B=1, Cin=1A · B · Cin

把这些项“或”起来,就能得到 S。

至于 Cout,它的生成条件更直观:只要任意两位为1,就可能产生进位。最终表达式为:
$$
C_{out} = A \cdot B + C_{in} \cdot (A \oplus B)
$$
但我们不能用 ⊕,所以也得拆成基本门组合。

Verilog 实现:还原门级细节

下面这段代码完全避开 XOR 操作符,纯粹使用 AND/OR/NOT 构建全加器逻辑:

module full_adder( input A, input B, input Cin, output S, output Cout ); wire not_A, not_B, not_Cin; assign not_A = ~A; assign not_B = ~B; assign not_Cin = ~Cin; // Sum = A'B'Cin + A'BCin' + AB'Cin' + ABCin assign S = (not_A & not_B & Cin) | (not_A & B & not_Cin) | (A & not_B & not_Cin) | (A & B & Cin); // Carry: 分解为多个产生进位的情况 assign Cout = (A & B) | (B & Cin) | (A & Cin); endmodule

等等,Cout 怎么变简单了?

没错!前面我们写的布尔式可以进一步化简。原始形式(A·B) + (Cin·(A⊕B))展开后其实等价于(A·B) + (A·Cin) + (B·Cin)—— 这正是经典的“多数表决”逻辑:三者中有两个为1,则输出1。

这个优化不仅减少了门数量,还降低了延迟。你会发现,在教学中从真值表推导公式只是第一步,真正的工程思维在于如何简化与重构。


把单比特变成8位:串行进位的艺术

有了全加器,下一步就是把它复制八次,连成一条链。这就是所谓的串行进位加法器(Ripple Carry Adder)

想象一下:第0位开始计算,产生一个进位信号 C1;这个 C1 必须稳定下来,才能作为第1位的输入;接着第1位算完,又传出 C2……一直到第7位输出最终的 Cout。

整个过程就像多米诺骨牌,每一块都要等前一块倒下才开始行动。

结构清晰,代价明显

这种结构的最大优点是模块化强、易于理解。你看它的 Verilog 实现几乎是“复制粘贴”式的整齐:

module ripple_carry_adder_8bit( input [7:0] A, input [7:0] B, input Cin, output [7:0] S, output Cout ); wire [7:0] carry; full_adder fa0 (.A(A[0]), .B(B[0]), .Cin(Cin), .S(S[0]), .Cout(carry[0])); full_adder fa1 (.A(A[1]), .B(B[1]), .Cin(carry[0]), .S(S[1]), .Cout(carry[1])); full_adder fa2 (.A(A[2]), .B(B[2]), .Cin(carry[1]), .S(S[2]), .Cout(carry[2])); full_adder fa3 (.A(A[3]), .B(B[3]), .Cin(carry[2]), .S(S[3]), .Cout(carry[3])); full_adder fa4 (.A(A[4]), .B(B[4]), .Cin(carry[3]), .S(S[4]), .Cout(carry[4])); full_adder fa5 (.A(A[5]), .B(B[5]), .Cin(carry[4]), .S(S[5]), .Cout(carry[5])); full_adder fa6 (.A(A[6]), .B(B[6]), .Cin(carry[5]), .S(S[6]), .Cout(carry[6])); full_adder fa7 (.A(A[7]), .B(B[7]), .Cin(carry[6]), .S(S[7]), .Cout(carry[7])); assign Cout = carry[7]; endmodule

但问题也很现实:速度慢

假设每个全加器的进位传播延迟是 50ns(在74HC逻辑中很常见),那么整个8位加法器最坏情况下的延迟就是 8 × 50ns =400ns。这意味着最高工作频率不超过 2.5MHz —— 对现代系统来说几乎不可接受。

但这恰恰让我们看清了一个关键设计权衡:面积 vs. 速度。RCA 占用资源少、结构规整,适合低速控制、教学演示或资源极度受限的场景;而追求性能的地方,则必须引入超前进位等高级结构。


动手实践:面包板上的“微型ALU”

理论讲完,该接线了。

你可以用以下芯片在面包板上搭建整个系统:

功能芯片型号类型
与门74HC08四路2输入AND
或门74HC32四路2输入OR
非门74HC04六路反相器

每个全加器大约需要:
- 2个与门(用于生成部分乘积)
- 1个或门(合并进位)
- 若干非门(取反输入)

总共八组,外加一些连接线和去耦电容。

实际搭建建议

  1. 电源处理:每块IC旁边放一个0.1μF陶瓷电容,接地脚附近走短线,防止开关噪声引发误触发。
  2. 输入设置:用 DIP 拨码开关提供 A[7:0] 和 B[7:0],通过上拉电阻确保高电平稳定。
  3. 输出显示:和值 S[7:0] 接 LED 或七段数码管驱动(如74HC4511),Cout 单独接红灯表示溢出。
  4. 初始进位 Cin:通常接地(0),但如果想做减法,可以把 Cin 接 1,并将 B 取反(补码机制)。
  5. 测试点预留:把 carry[0] 到 carry[7] 引出来,方便用示波器观察进位波形传播。

当你拨动开关,按下复位键,LED依次亮起,最后一位突然翻转并点亮 Cout 灯时——那一刻你会真切感受到:这不是魔法,是逻辑的力量


教学之外:为什么还要学这些“过时”的东西?

有人问:现在谁还用手搭逻辑门?FPGA 一行代码搞定的事,何必这么麻烦?

答案是:因为理解底层,才能驾驭高层

  • 当你在 Verilog 中写下assign sum = a + b;,综合工具会自动选择最优结构(可能是CLA或混合结构)。但如果你不懂进位传播的本质,就无法分析时序报告中的关键路径。
  • 当你的 FPGA 设计跑不到预期频率,问题很可能出在加法器这类组合逻辑上。你知道该怎么加流水线吗?怎么切分进位组?
  • 在抗辐射、航天或定制ASIC领域,工程师仍需手动绘制门级网表。那时候,你靠的就是对基本单元的深刻理解。

更重要的是,这个项目教会你一种思维方式:从原子单元出发,逐层构建复杂系统。这是所有系统工程的核心方法论。


更进一步的可能性

一旦你掌握了 RCA,就可以尝试升级:

  • 加入超前进位逻辑:用 P/G(Generate/Propagate)信号提前预测进位,大幅缩短延迟。
  • 改为同步设计:加上时钟和寄存器,把组合逻辑封装成时序模块,提升稳定性。
  • 扩展为 ALU:增加控制信号,支持减法、与、或、异或等操作,真正做出一个简易算术逻辑单元。
  • 移植到 FPGA:用 Vivado 或 Quartus 综合,查看资源占用和时序分析结果,对比手工优化与工具优化的差异。

甚至有人用纯74系列芯片做出了完整的8位CPU(比如 Ben Eater 的经典项目)。他们的第一步,就是这样一个基于与或非门的加法器。


写在最后:每一个工程师的“成人礼”

回到最初的问题:为什么要用最笨的方法做一个加法器?

因为它逼你停下来思考每一根线、每一个门的作用。它让你明白,计算机不是天生就会算数的黑箱,而是由一个个确定性的逻辑门构成的精密机器。

当你第一次看到自己搭建的电路正确输出255 + 1 = 0并点亮溢出灯时,那种成就感,堪比写出第一个“Hello World”。

而这,正是每一位硬件工程师成长路上不可或缺的“成人礼”。

如果你正在学习数字电路、准备参加电子竞赛,或者只是想找回动手的乐趣——不妨今晚就打开仿真软件,或者拿起焊台,从一个与门开始,走出属于你的第一条进位链。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询