uacs2024

导航

leetcode477. 汉明距离总和

477. 汉明距离总和

微信截图_20251022202824

🤡过不了的暴力解:

class Solution {
    public int totalHammingDistance(int[] nums) {
        int n = nums.length,res = 0;
        for(int i = 0;i < n;++i){
            for(int j = i + 1;j < n;++j){
                res += HammingDist(nums[i],nums[j]);
            }
        }
        return res;
    }

    public int HammingDist(int x,int y){
        int z = x ^ y,res = 0;
        while(z > 0){
            z &= (z - 1);++res;
        }
        return res;
    }
}

法一

在计算汉明距离时,我们考虑的是同一比特位上的值是否不同,而不同比特位之间是互不影响的。

对于数组 nums 中的某个元素 val,若其二进制的第 i 位为 1,我们只需统计 nums 中有多少元素的第 i 位为 0,即计算出了 val 与其他元素在第 i 位上的汉明距离之和。

具体地,若长度为 n 的数组 nums 的所有元素二进制的第 i 位共有 c 个 1,n−c 个 0,则些元素在二进制的第 i 位上的汉明距离之和为 c⋅(n−c)

我们可以从二进制的最低位到最高位,逐位统计汉明距离。将每一位上得到的汉明距离累加即为答案。具体实现时,对于整数 val 二进制的第 i 位,我们可以用代码 (val >> i) & 1 来取出其第 i 位的值。

此外,由于 10^9<2^30,我们可以直接从二进制的第 0 位枚举到第 29 位。

class Solution {
    public int totalHammingDistance(int[] nums) {
        int n = nums.length,res = 0;
        for(int i = 0;i < 30;++i){
            int countOne = 0;//统计本次右移之后末位为1的元素个数
            for(int num : nums){
                countOne += (num >> i) & 1;
            }
            res += countOne * (n - countOne);//本次右移末尾的汉明距离加到res
        }
        return res;
    }
}

 

posted on 2025-10-22 20:36  ᶜʸᵃⁿ  阅读(2)  评论(0)    收藏  举报