当前位置: 首页 > news >正文

[特殊字符] 蓝桥杯 Java B 组 之位运算(异或性质、二进制操作)

Day 6:位运算(异或性质、二进制操作)


📖 一、位运算简介

位运算是计算机底层优化的重要手段,利用二进制操作可以大大提高运算速度。常见的位运算包括:

  • 与(&)a & b,如果两个二进制位都为 1,结果为 1,否则为 0
  • 或(|)a | b,如果两个二进制位中至少有一个为 1,结果为 1,否则为 0
  • 异或(^)a ^ b,如果两个二进制位不同,结果为 1,否则为 0
  • 取反(~)~a,按位取反,0110
  • 左移(<<)a << n,将 a 的二进制表示向左移动 n 位,相当于 a * 2^n
  • 右移(>>)a >> n,将 a 的二进制表示向右移动 n 位,相当于 a / 2^n(保留符号位)。
  • 无符号右移(>>>):不保留符号位,即高位补 0

📖 二、只出现一次的数字(Single Number)

🔹 1. 题目描述

给定一个非空整数数组,除了某个数字只出现一次以外,其他数字均出现两次。请找出这个只出现一次的数字。

示例

输入: nums = [4, 1, 2, 1, 2]
输出: 4

🔹 2. 思路与分析

  • 利用异或运算 ^
    • 性质1a ^ a = 0,任意数与自身异或为 0
    • 性质2a ^ 0 = a,任意数与 0 异或仍是自身。
    • 性质3:异或满足交换律结合律,即 a ^ b ^ c = a ^ c ^ b,顺序无关。
    • 性质4a ^ b ^ b = a,某个数字 b 出现偶数次,它们会相互抵消。

因此,将所有数字进行异或操作,所有成对出现的数字都会抵消为 0,最终结果就是那个只出现一次的数字。


🔹 3. 代码实现(只出现一次的数字)

public class SingleNumber {
    public int findSingleNumber(int[] nums) {
        int result = 0;
        for (int num : nums) {
            result ^= num; // 利用异或运算找出唯一的数
        }
        return result;
    }

    public static void main(String[] args) {
        SingleNumber solution = new SingleNumber();
        int[] nums = {4, 1, 2, 1, 2};
        System.out.println("只出现一次的数字: " + solution.findSingleNumber(nums)); // 输出 4
    }
}

🔹 4. 代码讲解

  • result ^= num:将数组中的所有数字进行异或。
  • 成对的数字会被消除,只剩下唯一出现一次的数字。

✅ 时间复杂度:O(n),只需遍历一次数组。
✅ 空间复杂度:O(1),只使用一个变量存储结果。


📖 三、二进制中 1 的个数(Hamming Weight)

🔹 1. 题目描述

编写一个函数,计算一个整数的二进制表示中 1 的个数。

示例

输入: n = 9  (1001)
输出: 2

🔹 2. 思路与分析

方法 1️⃣:位运算逐位检查

  1. 每次检查 n 的最低位是否为 1n & 1)。
  2. 右移 n 一位(n >>= 1),直到 n 变为 0

方法 2️⃣:n & (n - 1) 高效算法

  • 性质n & (n - 1) 可以移除 n 最右边的 1,这样 1 的个数就等于操作 n & (n - 1) 多少次。

🔹 3. 代码实现(方法 1:逐位检查)

public class HammingWeight {
    public int countOnes(int n) {
        int count = 0;
        while (n != 0) {
            count += (n & 1); // 检查最低位是否为1
            n >>= 1; // 右移一位
        }
        return count;
    }

    public static void main(String[] args) {
        HammingWeight solution = new HammingWeight();
        int n = 9; // 二进制: 1001
        System.out.println("二进制中 1 的个数: " + solution.countOnes(n)); // 输出 2
    }
}

🔹 4. 代码实现(方法 2:n & (n - 1)

public class HammingWeightOptimized {
    public int countOnes(int n) {
        int count = 0;
        while (n != 0) {
            n &= (n - 1); // 清除最低位的1
            count++;
        }
        return count;
    }

    public static void main(String[] args) {
        HammingWeightOptimized solution = new HammingWeightOptimized();
        int n = 9; // 二进制: 1001
        System.out.println("二进制中 1 的个数: " + solution.countOnes(n)); // 输出 2
    }
}

🔹 5. 代码讲解

方法 1:

  • 时间复杂度 O(log n),因为 n 的二进制长度最多为 log n
  • 空间复杂度 O(1)

方法 2:

  • 时间复杂度 O(k),其中 kn1 的个数,比 O(log n) 更快。
  • 空间复杂度 O(1)

n & (n - 1) 计算次数等于 1 的个数,比 O(log n) 更快


📖 四、位运算总结

1. 常用位运算技巧

运算作用
a & 1判断 a 是否为奇数
`a(1 << k)`
a & ~(1 << k)a 的第 k 位置 0
a ^ (1 << k)翻转 a 的第 k
n & (n - 1)清除 n 的最低位 1
n & (-n)获取 n 的最低位 1

2. 位运算的常见应用

  1. 判断奇偶数n & 1 == 1(奇数),n & 1 == 0(偶数)。
  2. n 的二进制中 1 的个数
  3. 交换两个数a = a ^ b; b = a ^ b; a = a ^ b;(不使用额外空间)。
  4. 判断 n 是否是 2 的幂n > 0 && (n & (n - 1)) == 0

🎯 练习建议

  1. 理解异或运算的性质,练习 "只出现一次的数字"
  2. 熟练掌握 n & (n - 1),用于清除最低位 1 的优化技巧。
  3. 多做位运算相关题目,包括位掩码、二进制操作

相关文章:

  • Linux第十三节 — 进程状态详解
  • sklearn中的决策树-分类树:重要参数
  • reacct hook useState
  • RT-Thread+STM32L475VET6——icm20608传感器
  • Maven 基础环境搭建与配置(一)
  • 固态电容寿命
  • 【Java学习】抽象类与接口
  • 14.5 基于LangChain重构Auto-GPT:新一代自主智能体架构设计实践
  • Deepseek存算分离安全部署手册
  • Baklib革新数字化内容管理流程安全策略
  • Git常见命令--助力开发
  • 论文绘图工具
  • 【多模态处理篇八】【DeepSeek增强现实:AR导航实时推理优化】
  • Vue 不同大版本与 Node.js 版本匹配的详细参数
  • 蓝桥杯真题 - 缴纳过路费 - 题解
  • 【Agent的革命之路——LangGraph】工作流中的 Command 模式
  • 【C语言】(一)数据在计算机中的存储与表示
  • 解决Excel文件格式损坏问题:如何通过程序读取并复制内容
  • MySQL 中的索引数量是否越多越好?
  • hot100_139. 单词拆分
  • 巴方称印军发动24起袭击,巴境内6处地点遭袭致8人死亡
  • 【社论】跑赢12级狂风,敦煌做对了什么
  • 非洲中青年军官代表团访华,赴北京、长沙、韶山等地参访交流
  • 巴基斯坦宣布禁止与印度的进口贸易
  • 视频丨054B型护卫舰钦州舰南海实战化训练
  • 泽连斯基拒绝普京72小时停火提议,坚持应尽快实现30天停火