题目重点:从 Oracle 六阶段面经中的 a=30、b=40 交换题出发,验证 XOR 三步,并解释类型、别名和可读性。
题意与假设
这道练习题保留了面经中值得训练的核心约束,并将需要澄清的条件单独列出。现场拿到变体时,先和面试官确认这些条件。
- 训练版 a、b 是两个不同的整数变量;展示 Python 函数返回交换后的二元组,返回结构不计入面试题的临时变量限制。
- XOR 作用于整数;浮点、字符串和对象引用不适用此推导。
解题路线
- 第一步 a=a XOR b,使 a 含两者差异;第二步 b=b XOR a,利用 x XOR x=0 得到原 a。
- 第三步 a=a XOR b,消去原 a,得到原 b;代入 30 与 40 手算或运行断言。
- 说明实际工程里常规临时变量或语言原生 swap 更清晰;若题目强制无第三变量,才用此技巧。对同一存储位置执行原地 XOR swap 的语言可能把值清零,需先检查是否别名。
手动走一遍
a=30、b=40:第一步 a=54;第二步 b=54 XOR 40=30;第三步 a=54 XOR 30=40。若 a=b=7 且是不同变量,三步仍得到 7、7。
Python 参考实现
下面的代码按上文假设实现,适合本地运行并追加自己的测试用例。
代码区可横向滚动;使用键盘时,先聚焦代码区再按方向键查看。
"""Swap two distinct integer variables without a third storage variable."""
def swap_without_third(a: int, b: int) -> tuple[int, int]:
a ^= b
b ^= a
a ^= b
return a, b
复杂度
固定宽度整数时间 O(1)、额外存储 O(1);Python 大整数按位运算的真实时间与字长有关,不能声称任意精度值恒定成本。
易错点与追问
容易失分的边界
- 把加减交换当作无溢出方案,在固定宽度有符号整数中可能溢出。
- 对同一地址的两个引用执行原地 XOR swap。
- 把面试技巧误认为比普通 swap 更可维护。
继续深挖
- Python 的 a,b=b,a 为何更易读,其求值时有没有临时对象?
- 如果参数是同一个数组元素的别名,如何避免 XOR 自清零?
- 定长整数与任意精度整数的成本有何不同?
