Appearance
题目
某 32 位计算机按字节编址,采用小端(Little Endian)方式。若语句 int i=0 对应指令的机器代码为 C7 45 FC 00 00 00 00,则语句 int i=-64 对应指令的机器代码是( )。
错因
B
把 -64 的补码末两位算反了:写成 0C 而不是 C0。可能是把 1100_0000 的两个十六进制位写颠倒了——0xC0 的高 4 位是 1100、低 4 位是 0000,写错位置就成了 0x0C(高 4 位 0000、低 4 位 1100)。
C
把字节顺序整体反过来——按大端排:高字节在低地址(FF FF FF C0)。这是没记住小端"低地址放低字节"的规则。题目明说小端,要按"低字节先出现"排。
D
两个错叠加:① 字节顺序按大端来(FF 在前)② 末字节又写成 0C 而非 C0。等于把 B 和 C 的错都犯了。
总解析
第一步:理解给定指令的结构
int i = 0 → 机器代码 C7 45 FC | 00 00 00 00
可以推断:
| 字节段 | 含义 |
|---|---|
C7 45 FC | 机器指令 + 寻址信息(如 MOV [栈帧 + FC] 这类操作) |
00 00 00 00 | 立即数 0(int 占 4 字节) |
int i = -64 的指令前缀完全相同(操作和地址都没变),只需把后 4 字节立即数改为 -64 的小端表示。
第二步:求 -64 的 32 位补码
| 步骤 | 二进制末段 | 十六进制 |
|---|---|---|
| +64 | 0100 0000 | 0x40 |
| 32 位填 0 | 0000...0000 0100 0000 | 0x00000040 |
| 取反 | 1111...1111 1011 1111 | 0xFFFFFFBF |
| 加 1 | 1111...1111 1100 0000 | 0xFFFFFFC0 |
-64 的 32 位补码 = 0xFFFFFFC0。
第三步:按小端拆字节
小端规则:最低字节在最低地址(即出现在最前面)。
把 0xFFFFFFC0 按字节从低到高拆开:
| 字节序号 | 字节值 |
|---|---|
| 最低字节(B0) | C0 |
| B1 | FF |
| B2 | FF |
| 最高字节(B3) | FF |
写入指令立即数段:C0 FF FF FF。
第四步:拼整条指令
最终答案是 A(C7 45 FC C0 FF FF FF)。
对照参考指令验证(int i = 0):
| 立即数(小端 4 字节) | 真值 |
|---|---|
00 00 00 00 | 0 ✓ |
C0 FF FF FF | 反过来读 = FF FF FF C0 = 0xFFFFFFC0 = -64 ✓ |
易错点速查:
- 小端字节序 = 数据按字节从右往左"倒着"写入内存
- 0xC0 ≠ 0x0C — 一个字节里两个十六进制位不能颠倒
- -64 的 32 位补码 ≠ 简单的 0x40 加负号——必须按"取反加 1"展开到完整的 0xFFFFFFC0