Integer.bitCount() 是 Java 中用于计算一个整数的二进制表示中“1”的个数(即 Hamming WeightPopulation Count)的高效静态方法。它在算法优化、位运算、密码学、数据压缩等领域有广泛应用。


一、方法定义

public static int bitCount(int i)
  • 所属类java.lang.Integer
  • 访问修饰符public static
  • 参数int i —— 要计算的整数(支持负数)
  • 返回值:该整数二进制表示中 1 的个数(int 类型)
  • 异常:无异常抛出

✅ 该方法对正数和负数均有效,因为它直接操作整数的 32 位补码表示。


二、功能说明

计算一个 int 类型数值的 二进制形式中 1 的个数

  • 正数:按其二进制表示计算。
  • 负数:按其 32 位补码 形式计算(结果仍是有效计数)。

📌 别名

  • Hamming Weight
  • Population Count (popcount)

三、示例代码

示例 1:基本用法(正数)

int num = 7; // 二进制: 00000000 00000000 00000000 00000111
int count = Integer.bitCount(num);
System.out.println(count); // 输出:3

示例 2:不同数值的位数统计

System.out.println(Integer.bitCount(0));     // 0 → 0 个 1
System.out.println(Integer.bitCount(1));     // 1 → 1 个 1
System.out.println(Integer.bitCount(2));     // 10 → 1 个 1
System.out.println(Integer.bitCount(3));     // 11 → 2 个 1
System.out.println(Integer.bitCount(15));    // 1111 → 4 个 1
System.out.println(Integer.bitCount(255));   // 11111111 → 8 个 1

示例 3:负数处理(关键!)

int negative = -1;
// -1 的补码:32 个 1 → 11111111 11111111 11111111 11111111
System.out.println(Integer.bitCount(-1));    // 输出:32

System.out.println(Integer.bitCount(-2));    // 输出:31
// -2 补码: 111...110 → 31 个 1

示例 4:2 的幂次方

// 2 的幂次方二进制只有一个 1
System.out.println(Integer.bitCount(8));     // 1000 → 输出:1
System.out.println(Integer.bitCount(16));    // 10000 → 输出:1
System.out.println(Integer.bitCount(1024));  // 10000000000 → 输出:1

四、使用技巧

1. 判断是否为 2 的幂次方

一个正整数是 2 的幂次方,当且仅当 bitCount(n) == 1

public static boolean isPowerOfTwo(int n) {
    return n > 0 && Integer.bitCount(n) == 1;
}

System.out.println(isPowerOfTwo(8));   // true
System.out.println(isPowerOfTwo(10));  // false

2. 计算两个数的汉明距离(Hamming Distance)

汉明距离 = 两数异或后 bitCount 的结果

int x = 1; // 01
int y = 4; // 100
int distance = Integer.bitCount(x ^ y); // 101 → 2 个 1
System.out.println(distance); // 输出:2

3. 统计集合中元素个数(位图场景)

int 的每一位表示一个布尔状态(如权限、选项)

int flags = 0b101101; // 表示第 0,2,3,5 位被选中
int selectedCount = Integer.bitCount(flags);
System.out.println("选中项数量: " + selectedCount); // 输出:4

4. 奇偶校验位计算

boolean hasEvenParity = (Integer.bitCount(data) % 2) == 0;

五、常见错误与注意事项

问题 说明 建议
误解负数结果 认为 -1bitCount 应为 1,实际是 32 理解其基于 32 位补码
忽略符号位影响 负数高位全是 1,导致 1 的数量很多 在业务逻辑中根据需求处理
性能误解 认为它是简单循环,实际是高度优化的算法 可放心在高频场景使用

六、底层实现原理(简化版)

Integer.bitCount() 使用了 分治法 + 位并行运算,避免逐位判断,性能极高。

以下是其核心思想的简化版本:

public static int bitCount(int i) {
    // 将每 2 位一组,统计 1 的个数
    i = i - ((i >>> 1) & 0x55555555);
    // 每 4 位合并
    i = (i & 0x33333333) + ((i >>> 2) & 0x33333333);
    // 每 8 位合并
    i = (i + (i >>> 4)) & 0x0f0f0f0f;
    // 累加到高 8 位
    i = i + (i >>> 8);
    i = i + (i >>> 16);
    return i & 0x3f;
}

✅ 时间复杂度:O(1),仅需常数次位运算。


七、与其他方法对比

方法 功能 性能 适用场景
Integer.bitCount(i) 计算 1 的个数 ⭐⭐⭐⭐⭐ (极快) 推荐首选
手动循环移位 while(i!=0) { count += i&1; i>>>=1; } ⭐⭐ (慢) 教学理解
Integer.toBinaryString(i).replace("0", "").length() 字符串方式 ⭐ (极慢) 不推荐

结论:永远优先使用 bitCount(),不要手动实现。


八、最佳实践

✅ 推荐做法

  1. 用于算法题中的位统计

    // LeetCode 常见题型
    int count = Integer.bitCount(n);
    
  2. 性能敏感场景(如游戏、高频交易)

    • 位图压缩、状态机、权限校验等
  3. 结合位运算进行逻辑判断

    if (Integer.bitCount(options) >= 3) {
        // 至少选择了 3 个选项
    }
    
  4. Integer.numberOfLeadingZeros() 配合使用

    int highestBitPos = 31 - Integer.numberOfLeadingZeros(n);
    int ones = Integer.bitCount(n);
    

九、性能分析

  • 时间复杂度:O(1),固定步数完成
  • JVM 优化:现代 JVM 会将其优化为单条 CPU 指令(如 x86 的 POPCNT
  • 性能极高:远快于任何手动循环或字符串操作

✅ 在 JDK 源码中被广泛用于 HashMapBitSet 等核心类。


十、总结

项目 内容
核心功能 计算 int 二进制中 1 的个数(Hamming Weight)
支持负数 ✅ 基于 32 位补码计算
返回值 int,范围 0~32
典型用途 位运算、算法优化、数据压缩、权限统计
性能 ⭐⭐⭐⭐⭐ 极高,推荐首选
最佳实践 用于判断 2 的幂、汉明距离、集合大小等
常见误区 期望负数返回小值,实际是补码计数

💡 一句话总结
Integer.bitCount() 是 Java 中最高效的“1 的个数”计算方法,基于位并行算法实现,适用于所有整数(含负数),是位运算编程的必备工具。