(LeetCode-Hot100)461. 汉明距离

问题简介

461. 汉明距离 - LeetCode

题目描述

两个整数之间的 汉明距离 指的是这两个数字对应二进制位不同的位置的数目。

给你两个整数 xy,计算并返回它们之间的汉明距离。


示例说明

示例 1:

复制代码
输入:x = 1, y = 4
输出:2
解释:
1   (0 0 0 1)
4   (0 1 0 0)
       ↑   ↑
上面的箭头指出了对应二进制位不同的位置。

示例 2:

复制代码
输入:x = 3, y = 1
输出:1

解题思路

💡 方法一:异或 + 逐位计数(推荐)

核心思想:

  • 两个数异或(XOR)后,结果中为 1 的位即为两数二进制表示不同的位置。
  • 统计异或结果中 1 的个数即可。

步骤:

  1. 计算 x ^ y 得到差异位。
  2. 统计该结果中二进制 1 的个数。
    • 可通过不断右移并检查最低位是否为 1 实现。
    • 或使用 n & (n - 1) 技巧快速清除最低位的 1

💡 方法二:内置函数(语言特性)

  • Java: Integer.bitCount(x ^ y)
  • Go: bits.OnesCount(uint(x ^ y))

✅ 简洁高效,但需了解语言特性。


💡 方法三:逐位比较(不推荐,效率低)

  • 分别取出 xy 的每一位进行比较。
  • 需处理到最高有效位。

❌ 时间复杂度高,代码冗长。


代码实现

java 复制代码
class Solution {
    // 方法一:异或 + 逐位计数
    public int hammingDistance(int x, int y) {
        int xor = x ^ y;
        int count = 0;
        while (xor != 0) {
            count += xor & 1;  // 检查最低位是否为1
            xor >>>= 1;        // 无符号右移
        }
        return count;
    }

    // 方法一优化:使用 n & (n - 1) 清除最低位1
    public int hammingDistanceOptimized(int x, int y) {
        int xor = x ^ y;
        int count = 0;
        while (xor != 0) {
            count++;
            xor &= xor - 1;  // 清除最低位的1
        }
        return count;
    }

    // 方法二:内置函数
    public int hammingDistanceBuiltIn(int x, int y) {
        return Integer.bitCount(x ^ y);
    }
}
go 复制代码
package main

import "math/bits"

func hammingDistance(x int, y int) int {
    // 方法一:异或 + 逐位计数
    xor := x ^ y
    count := 0
    for xor != 0 {
        count += xor & 1
        xor >>= 1
    }
    return count
}

// 方法一优化:使用 n & (n - 1)
func hammingDistanceOptimized(x int, y int) int {
    xor := x ^ y
    count := 0
    for xor != 0 {
        count++
        xor &= xor - 1
    }
    return count
}

// 方法二:内置函数
func hammingDistanceBuiltIn(x int, y int) int {
    return bits.OnesCount(uint(x ^ y))
}

示例演示

📌 x = 1, y = 4 为例:

步骤 操作 二进制表示 说明
1 x ^ y 0001 ^ 0100 = 0101 异或得到差异位
2 统计 01011 的个数 0101 → 2 个 1 汉明距离为 2

✅ 输出:2,符合预期。


答案有效性证明

  • 正确性 :异或运算的性质保证了只有在两个位不同时结果为 1,因此统计 1 的数量即为不同位的数量。
  • 边界情况
    • x == y → 异或为 0 → 距离为 0
    • x = 0, y = 2^31 - 1 → 所有位都不同 → 距离为 31
  • 数学依据 :汉明距离定义与异或结果中 1 的数量完全等价。

复杂度分析

方法 时间复杂度 空间复杂度 说明
异或 + 逐位右移 O ( l o g m a x ( x , y ) ) O(\\log \\max(x, y)) O(logmax(x,y)) O ( 1 ) O(1) O(1) 最多 32 位
异或 + n & (n-1) O ( k ) O(k) O(k) O ( 1 ) O(1) O(1) k k k 为 1 的个数,最坏仍为 32
内置函数 O ( 1 ) O(1) O(1)(硬件优化) O ( 1 ) O(1) O(1) 实际由 CPU 指令加速

💡 在实际应用中,n & (n - 1) 方法通常更快,因为跳过了 0 位。


问题总结

关键点回顾:

  • 汉明距离 = 二进制不同位的数量。
  • 异或 是解决此类"位差异"问题的核心操作。
  • 统计二进制中 1 的个数是常见子问题,掌握 n & (n - 1) 技巧非常有用。

📌 延伸思考:

  • 若扩展到多个数,可考虑使用 Trie 或位运算批量处理。
  • 在通信、编码理论中,汉明距离用于衡量纠错能力。

💡 一句话总结:

"异或找不同,数一得答案。"

github地址: https://github.com/swf2020/LeetCode-Hot100-Solutions

相关推荐
宝贝儿好1 天前
【强化学习实战】第十一章:Gymnasium库的介绍和使用(1)、出租车游戏代码详解(Sarsa & Q learning)
人工智能·python·深度学习·算法·游戏·机器学习
pao__pao_1 天前
计算机系统大作业 程序人生-Hello’s P2P
程序人生·职场和发展·课程设计
java1234_小锋1 天前
Java高频面试题:Redis的Key和Value的设计原则有哪些?
java·redis·面试
munubak1 天前
程序人生-Hello’s P2P
程序人生·职场和发展
iPadiPhone1 天前
流量洪峰下的数据守护者:InnoDB MVCC 全实现深度解析
java·数据库·mysql·面试
努力学算法的蒟蒻1 天前
day109(3.10)——leetcode面试经典150
面试·职场和发展
Nuopiane1 天前
关于C#/Unity中单例的探讨
java·jvm·c#
芝士爱知识a1 天前
【程序人生】码农考公指南:是“降维打击”还是“围城自困”?
程序人生·职场和发展·程序员·公务员·考公·职场规划
win x1 天前
JVM类加载及双亲委派模型
java·jvm
炒鸡菜6661 天前
程序人生-Hello’s P2P
c语言·程序人生·职场和发展