JK 与 T 触发器、计数器理论:翻转的条件与任意进制计数
更新时间:2026-09-12。本文是「集成电路大类 · 芯片设计」入门层(beginner)数字逻辑基础第二十篇。锁存器与触发器 讲了最常用的 D 触发器,寄存器、计数器与移位寄存器给了 RTL 直觉;这一篇回到教科书,把另外两种经典触发器和计数器的设计理论补全。
本文要回答的问题
- SR 锁存器有个
S=R=1的非法态,JK 触发器是怎么消掉它的? - T 触发器是什么,「翻转(toggle)」为什么天然就是计数?
- JK、T、D 三种触发器怎么互相转换?现代设计为什么以 D 为中心?
- 异步(行波)计数器和同步计数器在时钟接法、速度、毛刺上差在哪?
- 怎么用通用二进制计数器搭出模 N(任意进制)计数器?分频和占空比怎么控制?
一、从 SR 的非法态到 JK 触发器
锁存器那篇讲过 SR 锁存器:S=1 置位、R=1 复位、S=R=0 保持。它有一个尴尬输入 S=R=1:两个输出被迫都为 1(不再互补),且两个输入同时撤去时最终落到 0 还是 1 取决于门延迟的竞争,结果不可预测——这是要避免的非法态。
JK 触发器在 SR 基础上做了两处改造:①把原来非法的 J=K=1(J 对应 S、K 对应 R)重新定义成一个有用的动作——翻转(toggle),即 Q 变成自己的反;②把输出 Q、Q̄ 反馈回输入门,形成「只在时钟沿采样、并根据当前状态决定动作」的结构。它的特性表:
| J | K | 时钟沿后 Q⁺ | 动作 |
|---|---|---|---|
| 0 | 0 | Q(不变) | 保持 hold |
| 0 | 1 | 0 | 复位 reset |
| 1 | 0 | 1 | 置位 set |
| 1 | 1 | Q̄(变反) | 翻转 toggle |
四种组合全部合法、没有未定义状态,这是 JK 相对 SR 的关键进步。正是多出的「翻转」能力,让它特别适合做计数器——计数到下一个数,本质就是某些 bit 在条件满足时翻转。
二、T 触发器:为计数而生
把 JK 的 J、K 两端短接在一起当一个输入端 T,就得到 T 触发器(toggle flip-flop):
| T | 时钟沿后 Q⁺ | 动作 |
|---|---|---|
| 0 | Q | 保持 |
| 1 | Q̄ | 翻转 |
T=1 时每来一个时钟沿 Q 就翻一次,T=0 时不动。特性方程简单到只有一个异或:Q⁺ = Q ⊕ T。一个 T 端恒接 1 的 T 触发器,输出频率恰是时钟的一半——这就是最朴素的 1 位二分频/模 2 计数器;把若干个 T 触发器级联,就能数更多位。
三、D/JK/T 互通:为什么现代设计只剩 D
三种触发器在逻辑功能上完全可以互相转换,掌握转换关系有助于看懂老电路图和教科书:
- JK→D:令
J=D、K=D̄(外加一个反相器)。D=1 置位、D=0 复位,正好实现 Q⁺=D; - JK→T:J=K=T,即上一节;
- D→T:让 D 端接
Q ⊕ T(一个异或门反馈现态),T=1 时 D=Q̄ 翻转、T=0 时 D=Q 保持; - D→JK:用一个小 MUX/组合逻辑把 JK 编码成
D = J·Q̄ + K̄·Q。
关键工程事实:标准单元库和 FPGA 里的时序元件几乎只有 D 触发器一种(LUT/FF)。JK、T 主要活在教科书和老式中小规模器件里;今天你在 RTL 里写「使能时加一」,综合器会自动把它映射成「D 触发器 + 使能时翻转所需的反馈逻辑」,物理上仍是 DFF,但逻辑分析时把它看成 T 触发器更直观。所以学 JK/T 不是为了例化它们,而是为了:①读懂计数器/分频老电路;②理解「翻转条件」这个分析计数器的核心语言。
四、异步(行波)计数器:简单但慢
先看最直观的多位计数。把 T′ 触发器(T 恒为 1)级联:最低位 Q0 每个时钟翻转,Q0 的输出当 Q1 的时钟、Q0 翻两次(一个完整周期)Q1 才翻一次,依次串下去。时钟脉冲像水波一样逐级传播,所以叫行波计数器(ripple counter),也叫异步计数器——各级触发器的时钟不是同一个。
它的好处是极其省器件、连接简单(74x93 之类经典芯片就是它),但有三个硬伤:
- 慢:新值要等翻转波从最低位一路传到最高位才稳定,总延迟是各级延迟之和,位数越多越慢;
- 中间态与译码毛刺:进位传播过程中输出会短暂经过错误的中间值(如
011→100可能瞬间闪过001、101),若直接拿去做组合译码,会产生竞争冒险毛刺; - 不利于时序分析:各级时钟相位错开、且来自普通数据通路而非专用时钟网络,skew 大、STA 难做。这正是 FPGA 纪律「别用分频/翻转输出当时钟、时钟走全局网络」针对的反例。
五、同步计数器:共用时钟,用使能控制进位
主流做法是同步计数器:所有位的时钟端都接同一个 clk,谁该翻转由各自的使能条件(逻辑上的 T)决定。一个 n 位二进制加法计数器,第 i 位的翻转条件是「所有更低位都已经是 1」:
T0 = 1
T1 = Q0
T2 = Q0·Q1
T3 = Q0·Q1·Q2
...
Ti = Q0·Q1·...·Q(i-1)用进位链把「低位全 1」的使能逐位传下去(可用先行进位改善速度,思想类似 CLA 加法器)。所有翻转在同一个时钟沿发生,不存在行波中间态,译码干净、时序可分析。
对应到可综合 RTL,推荐写法是「时钟 + 时钟使能」而非造新时钟(见 同步设计原则):
// 模 2^W 同步使能计数器:使能 en 那拍才加一
always @(posedge clk or negedge rst_n)
if (!rst_n) cnt <= {W{1'b0}};
else if (en) cnt <= cnt + 1'b1;综合后 en 就是各级的翻转使能(T 条件的工程化身),时钟始终是那一个干净的高速时钟。需要慢节拍时用使能分频(每 N 个高速时钟脉冲让 en 有效一次),而不是把计数器输出反相当另一个时钟去驱动别的逻辑。
六、模 N 计数器与任意分频
二进制计数器天然模 2ⁿ(2、4、8、16…)。想要模 N(N 不是 2 的幂,如模 10、模 6),要让计数器在数到某个值时提前回到起点,跳过 2ⁿ−N 个状态。三种经典手法:
| 方法 | 做法 | 特点 |
|---|---|---|
| 复位法 | 用组合逻辑检测到 N(如模 10 检测 1010)立即异步/同步清零 | 简单;异步复位法状态 N 只短暂存在,可能有毛刺,推荐同步清零 |
| 置位法 | 数到末端时载入一个初值,使一个循环恰含 N 个状态 | 可从非 0 起点计数 |
| 同步载入法 | 用 load 把计数器在末态时装入 2ⁿ−N(补数),加法自然回卷 | 最干净,无瞬态,工程首选 |
例如模 10(BCD 十进制)计数器,同步法让它在 cnt==9 时下一拍载入 0:if(cnt==4'd9) cnt<=0; else cnt<=cnt+1;。务必检查自启动(见 同步时序电路分析设计):被跳过的那些状态若因干扰进入,要能在几拍内回到主循环,否则上电可能卡在野状态;RTL 里给次态逻辑写全 default/边界判断即可保证。
分频与占空比:模 N 计数器的进位输出(每 N 拍一个脉冲)频率是 fclk/N,但它是窄脉冲;要得到占空比 50% 的方波时钟,通常让计数器数到 N/2 翻转一次电平(偶数 N),或用专门的占空比逻辑。不过再次强调工程纪律:这种慢时钟绝大多数情况下应作为「时钟使能」去门控高速逻辑的动作,而不是真的接成另一个时钟树——后者会带来额外时钟域和 skew/CDC 问题(见 时钟与复位、CDC 基础)。
与现有篇目的衔接
- 前置:锁存器与触发器(SR/D、边沿触发)、寄存器、计数器与移位寄存器(RTL 直觉)
- 理论方法:同步时序电路分析与设计(状态表、自启动)
- 毛刺与时钟:竞争与冒险、时钟与复位、FPGA 同步设计原则
- 进阶:FSM 入门(带控制的复杂计数/时序)
总结
一句话总结:JK 触发器把 SR 锁存器非法的 J=K=1 重定义为「翻转」,四种输入组合全部合法从而消除了非法态;把 J、K 短接就得到计数专用的 T 触发器——T=1 每拍翻转、T=0 保持,特性方程 Q⁺=Q⊕T,且 D/JK/T 可互相转换(D 前加 D=Q⊕T 即 T、加 D=J·Q̄+K̄·Q 即 JK),但现代标准单元和 FPGA 只有 D 触发器,JK/T 是分析计数器的语言而非例化对象;多位计数器分两种哲学,行波(异步)计数器把低位输出当下一级时钟、省器件却因进位逐级传播而慢、存在错误中间态和译码毛刺、不利于 STA,同步计数器则让所有位共用一个时钟、用「所有更低位全 1」作每位的翻转使能 T,在同一沿动作、干净可分析;模 N 计数器用复位法、置位法或最干净的同步载入补数法跳过 2ⁿ−N 个多余状态,并要保证被跳过状态能回到主循环(自启动),分频输出频率为 fclk/N、需 50% 占空比时在 N/2 翻转电平,但工程上应把慢节拍当「时钟使能」而非另造时钟树,以避免额外时钟域、skew 与 CDC 问题。