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

优选算法的慧根之翼:位运算专题

专栏:算法的魔法世界

个人主页:手握风云

一、位运算

  • 基础位运算

        共包含6种&(按位与,有0就是0)、|(按位或有1就是1)、^(按位异或,相同为0,相异为1)、~(按位取反,0变成1,1变成0)、<<(左移)、>>(右移)。

  • 给定一个数n,确定它的二进制表示中第x位是0还是1

        我们先给出一个约定,以最低的一位为0位,从右向左依次递增。我们想确定第x位,只需让这一位数右移x位,再与1进行按位与操作。如果这一位是1,异或结果为1;如果这一位是0,异或结果为0。

  • 将一个数n的二进制表示的第x位修改为1

        只需要将第x位修改为1,其他位不变。我们只需要将1左移x位,再与之进行按位或操作。

  • 将一个数n的二进制表示的第x位修改为0

        与上面的操作思路差不多。先将1左移x位,再进行取反操作,再与之进行按位与操作。

  • 位图的思想

        位图的本质还是一个哈希表,哈希表的本质又是一个数组。现在我们可以用一个整型变量的比特位01来记录这些信息。

        我们直接使用n&(-n),而-n的求法可以先按位取反再加1。

  • 干掉一个数n二进制表示的最右侧的1

        就是把最右侧的1修改为0。n & (n-1),因为减1需要借位。

  • 运算的优先级

        位运算的符号太多,记起来太复杂了。我们只需要记住能加括号加括号

  • 异或运算的规律

        a ^ 0 = a;a ^ a = 0;a ^ b ^ c = a ^ (b ^ c)

二、例题讲解

2.1. 判定字符是否唯一

        第一种解法,使用哈希表。我们先遍历一遍字符串,看看这个字符在不在哈希表中,如果某个出现了两次,直接返回false。时间复杂度O(n),空间复杂度因为创建了哈希表,O(n)

class Solution {public boolean isUnique(String astr) {boolean[] hash = new boolean[128];for (int i = 0; i < astr.length(); i++) {char c = astr.charAt(i);if(hash[c]){return false;}hash[c] = true;}return true;}
}

        解法二:位图。建立一个大小为26的位图,用0来表示未出现,1来表示出现过一次。通过不断地判断某一位是否为1和修改为1,就可以判断字符是否为1。

        我们还可以用鸽巢原理进行优化:如果字符串长度大于26,那么一定存在重复的字符。

        完整代码实现:

public class Solution {public boolean isUnique(String astr){if(astr.length() > 26) return false;int BitMap = 0;for (int i = 0; i < astr.length(); i++) {int x = astr.charAt(i) - 'a';//先判断字符是否在位图中if(((BitMap >> x) & 1) == 1) return false;//把当前字符丢进位图中BitMap |= 1 << x;}return true;}
}

2.2. 丢失的数字

        解法1:创建一个大小为n+1的哈希表,利用数组元素与哈希表的下标一一对应的关系找出丢失的数字。时间复杂度和空间复杂度都为O(n)

        解法2:高斯求和。((首项+尾项)*项数)/2 - 数组的和。时间复杂度为O(n),空间复杂度为O(1)

        解法3:利用异或运算的定律。我们以示例1为例,我们用原始数组与完整的数进行异或运算,最终得到的结果就为丢失的数字。

        完整代码实现:

class Solution {public int missingNumber(int[] nums) {int ret = 0;for(int i : nums) ret ^= i;for (int i = 0; i <= nums.length; i++) {ret ^= i;}return ret;}
}

2.3. 两整数之和

        解法:异或位运算,因为异或位运算还可以有另一种理解,“无进位相加”,所以说我们接下来就要实现进位就可以。如下图,按位与正好能实现这种进位。

        但我们需要注意的是,进位不是进到它本身这一位来,而是要进到左边这一位上来,所以我们还需要将按位与的结果左移1位,直到左移的结果为0。

        完整代码实现:

class Solution {public int getSum(int a, int b) {while (b != 0) {int x = a ^ b;//先算出无进位相加的结果int carry = (a & b) << 1;//计算进位a = x;b = carry;}return a;}
}

2.4. 只出现一次的数字 II

        我们假设数组中出现三次的数字有n个,只出现一次的有1个,数组里的元素都是int类型的,我们从第0位开始遍历,让每一个数相同位数的比特位相加,那么它们的相加一共可以出现如下图4种情况。我们每遍历完一位,余数为0,就将只出现一次的数字该位的比特位修改为0;余数为1,就将只出现一次的数字该位的比特位修改为1。直到遍历到最后并修改一位比特位,找出只出现一次的数字。

        我们甚至还可以拓展到如果其他数字恰好出现n次,我们也可以利用上面的思路。

        完整代码实现:

class Solution {public int singleNumber(int[] nums) {int ret = 0;for (int i = 0; i < 32; i++) {int sum = 0;for(int x : nums)//依次统计nums中第i位的和if(((x >> i) & 1) == 1)sum++;sum %= 3;if(sum == 1) ret |= 1 << i;}return ret;}
}

2.5. 消失的两个数字

        我们先利用完整的数与原始数组进行异或操作,最终得到的结果为两个消失的数字的异或结果。我们假设tmp = a^b,下一步,找到tmp比特位中最右边的1。因为a与b是两个不同的数字,一定会存在相同位上不同的比特位,所以tmp的比特位一定会存在一位1。然后根据比特位上的不同,划分为两类异或。

        完整代码实现:

class Solution {public int[] missingTwo(int[] nums) {//先把所有数异或在一起int tmp = 0;for (int x : nums) tmp ^= x;for (int i = 0; i <= nums.length + 2; i++) tmp ^= i;//找到a、b不同的那一位int diff = 0;while (true) {if (((tmp >> diff) & 1) == 1) break;else diff++;}//根据diff位不同,分为两类异或int[] ret = new int[2];for (int x : nums) {if (((x >> diff) & 1) == 1) ret[1] ^= x;else ret[0] ^= x;}for (int i = 0; i <= nums.length + 2; i++) {if (((i >> diff) & 1) == 1) ret[1] ^= i;else ret[0] ^= i;}return ret;}
}

相关文章:

优选算法的慧根之翼:位运算专题

专栏&#xff1a;算法的魔法世界 个人主页&#xff1a;手握风云 一、位运算 基础位运算 共包含6种&(按位与&#xff0c;有0就是0)、|(按位或有1就是1)、^(按位异或&#xff0c;相同为0&#xff0c;相异为1)、~(按位取反&#xff0c;0变成1&#xff0c;1变成0)、<<(左…...

图论问题集合

图论问题集合 寻找特殊有向图&#xff08;一个节点最多有一个出边&#xff09;中最大环路问题特殊有向图解析算法解析步骤 1 &#xff1a;举例分析如何在一个连通块中找到环并使用时间戳计算大小步骤 2 &#xff1a;抽象成算法注意 实现 寻找特殊有向图&#xff08;一个节点最多…...

【数据结构】栈 与【LeetCode】20.有效的括号详解

目录 一、栈1、栈的概念及结构2、栈的实现3、初始化栈和销毁栈4、打印栈的数据5、入栈操作---栈顶6、出栈---栈顶6.1栈是否为空6.2出栈---栈顶 7、取栈顶元素8、获取栈中有效的元素个数 二、栈的相关练习1、练习2、AC代码 个人主页&#xff0c;点这里~ 数据结构专栏&#xff0c…...

实时目标检测新突破:AnytimeYOLO——随时中断的YOLO优化框架解析

目录 一、论文背景与核心价值 二、创新技术解析 2.1 网络结构革新:Transposed架构 2.2 动态路径优化算法 三、实验结果与性能对比 3.1 主要性能指标 3.2 关键发现 四、应用场景与部署实践 4.1 典型应用场景 4.2 部署注意事项 五、未来展望与挑战 一、论文背景与核心…...

Redis设计与实现-哨兵

哨兵模式 1、启动并初始化sentinel1.1 初始化服务器1.2 使用Sentinel代码1.3 初始化sentinel状态1.4 初始化sentinel状态的master属性1.5 创建连向主服务器的网络连接 2、获取主服务器信息3、获取从服务器的信息4、向主从服务器发送信息5、接受主从服务器的频道信息6、检测主观…...

C++进阶——封装哈希表实现unordered_map/set

与红黑树封装map/set基本相似&#xff0c;只是unordered_map/set是单向迭代器&#xff0c;模板多传一个HashFunc。 目录 1、源码及框架分析 2、模拟实现unordered_map/set 2.1 复用的哈希表框架及Insert 2.2 iterator的实现 2.2.1 iteartor的核心源码 2.2.2 iterator的实…...

第4.1节:使用正则表达式

1 第4.1节&#xff1a;使用正则表达式 将正则表达式用斜杠括起来&#xff0c;就能用作模式。随后&#xff0c;该正则表达式会与每条输入记录的完整文本进行比对。&#xff08;通常情况下&#xff0c;它只需匹配文本的部分内容就能视作匹配成功。&#xff09;例如&#xff0c;以…...

【算法day25】 最长有效括号——给你一个只包含 ‘(‘ 和 ‘)‘ 的字符串,找出最长有效(格式正确且连续)括号子串的长度。

32. 最长有效括号 给你一个只包含 ‘(’ 和 ‘)’ 的字符串&#xff0c;找出最长有效&#xff08;格式正确且连续&#xff09;括号子串的长度。 https://leetcode.cn/problems/longest-valid-parentheses/ 2.方法二&#xff1a;栈 class Solution { public:int longestValid…...

Jenkins + CICD流程一键自动部署Vue前端项目(保姆级)

git仓库地址&#xff1a;参考以下代码完成,或者采用自己的代码。 南泽/cicd-test 拉取项目代码到本地 使用云服务器或虚拟机采用docker部署jenkins 安装docker过程省略 采用docker部署jenkins&#xff0c;注意这里的命令&#xff0c;一定要映射docker路径&#xff0c;否则无…...

C 语言的未来:在变革中坚守核心价值

一、从 “古老” 到 “长青”&#xff1a;C 语言的不可替代性 诞生于 20 世纪 70 年代的 C 语言&#xff0c;历经半个世纪的技术浪潮&#xff0c;至今仍是编程世界的 “基石语言”。尽管 Python、Java 等高级语言在应用层开发中占据主流&#xff0c;但 C 语言在系统级编程和资…...

一款超级好用且开源免费的数据可视化工具——Superset

认识Superset 数字经济、数字化转型、大数据等等依旧是如今火热的领域&#xff0c;数据工作有一个重要的环节就是数据可视化。 看得见的数据才更有价值&#xff01; 现如今依旧有多数企业号称有多少多少数据&#xff0c;然而如果这些数据只是呆在冷冰冰的数据库或文件内则毫无…...

Vue3组合式API与选项式API的核心区别与适用场景

Vue.js作为现代前端开发的主流框架之一&#xff0c;在Vue3中引入了全新的组合式API(Composition API)&#xff0c;与传统的选项式API(Options API)形成了两种不同的开发范式。在当前开发中的两个项目中分别用到了组合式和选项式&#xff0c;故记录一下。本文将全面剖析这两种AP…...

RedHatLinux(2025.3.22)

1、创建/www目录&#xff0c;在/www目录下新建name和https目录&#xff0c;在name和https目录下分别创建一个index.htm1文件&#xff0c;name下面的index.html 文件中包含当前主机的主机名&#xff0c;https目录下的index.htm1文件中包含当前主机的ip地址。 &#xff08;1&…...

【C++篇】类与对象(上篇):从面向过程到面向对象的跨越

&#x1f4ac; 欢迎讨论&#xff1a;在阅读过程中有任何疑问&#xff0c;欢迎在评论区留言&#xff0c;我们一起交流学习&#xff01; &#x1f44d; 点赞、收藏与分享&#xff1a;如果你觉得这篇文章对你有帮助&#xff0c;记得点赞、收藏&#xff0c;并分享给更多对C感兴趣的…...

深搜专题13:分割回文串

描述 给你一个字符串 s&#xff0c;请你将 s 分割成一些子串&#xff0c;使每个子串都是回文串。返回 s 所有可能的分割方案数。 例如&#xff1a; 输入&#xff1a;“aab” 输出&#xff1a;2 2种方案数是[“a”,“a”,“b”]和[“aa”,“b”] 输入描述 一个字符串 s&#…...

OGG故障指南:OGG-01163 Bad column length (xxx) specified for column

报错 OGG-01163 Bad column length (xxx) specified for column AAA in table OWNER.TABLE, maximum allowable length is yyy原因 源端修改了字段长度。 虽然源端和目标端的长度已经通过DDL语句修改到一致&#xff0c;在extract进程未重启的情况下&#xff0c;生成的trail文…...

智慧运维平台:赋能未来,开启高效运维新时代

在当今数字化浪潮下&#xff0c;企业IT基础设施、工业设备及智慧城市系统的复杂度与日俱增&#xff0c;传统人工运维方式已难以满足高效、精准、智能的管理需求。停机故障、低效响应、数据孤岛等问题直接影响企业运营效率和成本控制。大型智慧运维平台&#xff08;AIOps, Smart…...

基于大语言模型的智能音乐创作系统——从推荐到生成

一、引言&#xff1a;当AI成为音乐创作伙伴 2023年&#xff0c;一款由大语言模型&#xff08;LLM&#xff09;生成的钢琴曲《量子交响曲》在Spotify冲上热搜&#xff0c;引发音乐界震动。传统音乐创作需要数年专业训练&#xff0c;而现代AI技术正在打破这一壁垒。本文提出一种…...

Reactive编程:什么是Reactive编程?Reactive编程思想

文章目录 **1. Reactive编程概述****1.1 什么是Reactive编程&#xff1f;****1.1.1 Reactive编程的定义****1.1.2 Reactive编程的历史****1.1.3 Reactive编程的应用场景****1.1.4 Reactive编程的优势** **1.2 Reactive编程的核心思想****1.2.1 响应式&#xff08;Reactive&…...

深度剖析:U盘突然无法访问的数据拯救之道

一、引言 在数字化办公与数据存储日益普及的当下&#xff0c;U盘凭借其小巧便携、即插即用的特性&#xff0c;成为了人们工作、学习和生活中不可或缺的数据存储工具。然而&#xff0c;U盘突然无法访问这一棘手问题却时常困扰着广大用户&#xff0c;它不仅可能导致重要数据的丢失…...

23种设计模式中的备忘录模式

在不破坏封装的前提下&#xff0c;捕获一个对象的内部状态&#xff0c;并允许在对象之外保存和恢复这些状态。 备忘录模式&#xff0c;主要用于捕获并保存一个对象的内部状态&#xff0c;以便将来可以恢复到该状态。 备忘录的模式主要由三个角色来实现&#xff1a;备忘录、发起…...

蓝桥杯-特殊的三角形(dfs/枚举/前缀和)

思路分析 深度优先搜索&#xff08;DFS&#xff09;思路 定义与参数说明 dfs 函数中&#xff0c;last 记录上一条边的长度&#xff0c;用于保证新选边长度大于上一条边&#xff0c;实现三边互不相等 。cnt 记录已选边的数量&#xff0c;当 cnt 达到 3 时&#xff0c;就构成了…...

我的编程之旅:从零到无限可能

一、自我介绍 大家好&#xff0c;我是望云山&#xff0c;一名智能科学与技术专业的大一学生 痴迷于用代码解决现实问题&#xff0c;尤其是自动化工具开发与智能硬件交互方向 2024年偶然用Python写了一个自动整理文件的脚本&#xff0c;第一次感受到“代码即魔法”的震撼 二、…...

一文详解k8s体系架构知识

0.云原生 1.k8s概念 1. k8s集群的两种管理角色 Master&#xff1a;集群控制节点&#xff0c;负责具体命令的执行过程。master节点通常会占用一股独立的服务器&#xff08;高可用部署建议用3台服务器&#xff09;&#xff0c;是整个集群的首脑。 Master节点一组关键进程&#xf…...

wx162基于springboot+vue+uniapp的在线办公小程序

开发语言&#xff1a;Java框架&#xff1a;springbootuniappJDK版本&#xff1a;JDK1.8服务器&#xff1a;tomcat7数据库&#xff1a;mysql 5.7&#xff08;一定要5.7版本&#xff09;数据库工具&#xff1a;Navicat11开发软件&#xff1a;eclipse/myeclipse/ideaMaven包&#…...

Baklib内容中台的核心优势是什么?

智能化知识管理引擎 Baklib的智能化知识管理引擎通过多源数据整合与智能分类技术&#xff0c;实现企业知识资产的自动化归集与动态更新。系统内置的语义分析算法可自动识别文档主题&#xff0c;结合自然语言处理技术生成结构化标签体系&#xff0c;大幅降低人工标注成本。针对…...

【C++】C++11介绍列表初始化右值引用和移动语义

个人主页 &#xff1a; zxctscl 如有转载请先通知 文章目录 1. C11简介2. 统一的列表初始化2.1&#xff5b;&#xff5d;初始化2.2 std::initializer_list 3. 声明3.1 auto3.2 decltype3.3 nullptr 4. 范围for循环4.1 范围for的语法4.2 范围for的使用条件 5. STL中一些变化6. 右…...

搜广推校招面经六十一

美团推荐算法 一、ANN算法了解么&#xff1f;说几种你了解的ANN算法 ANN 近似最近邻搜索&#xff08;Approximate Nearest Neighbor Search&#xff09;算法 1.1. KD-Tree&#xff08;K-Dimensional Tree&#xff0c;K 维树&#xff09; 类型: 空间划分数据结构适用场景: 低…...

人工智能与软件工程结合的发展趋势

AI与软件工程的结合正在深刻改变软件开发的流程、工具和方法&#xff0c;其发展方向涵盖了从代码生成到系统维护的整个生命周期。以下是主要的发展方向和技术趋势&#xff1a; 1. 软件架构体系的重构 从“面向过程”到“面向目标”的架构转型&#xff1a; AI驱动软件设计以目标…...

nacos 外置mysql数据库操作(docker 环境)

目录 一、外置mysql数据库原因&#xff1a; 二、数据库准备工作 三、构建nacos容器 四、效果展示 一、外置mysql数据库原因&#xff1a; 想知道nacos如何外置mysql数据库之前&#xff0c;我们首先要知道为什么要外置mysql数据库&#xff0c;或者说这样做有什么优点和好处&am…...