【vector题解】只出现一次的数字 | 电话号码的数字组合
只出现一次的数字
力扣(LeetCode)官网 - 全球极客挚爱的技术成长平台
给你一个整数数组 nums,其中恰好有两个元素只出现一次,其余所有元素均出现两次。 找出只出现一次的那两个元素。你可以按 任意顺序 返回答案。
你必须设计并实现线性时间复杂度的算法且仅使用常量额外空间来解决此问题。
示例 1:
输入:nums = [1,2,1,3,2,5]
输出:[3,5]
解释:[5, 3] 也是有效的答案。
示例 2:
输入:nums = [-1,0]
输出:[-1,0]
示例 3:
输入:nums = [0,1]
输出:[1,0]
思路
思路一:看到去重,先排序
上篇我们总结出了一个经验:看到去重,就先排个序。把大小相同的放在一起,这样,假如一个数的左邻右舍都跟它不一样,那这个数就是只出现了一次的那个。
这个道理 同样可应用于 这题。
class Solution {
public:vector<int> singleNumber(vector<int>& nums) {int sz = nums.size();vector<int> ret;//先考虑只有2 个元素的特殊情况if (sz == 2) { for (int e : nums) {ret.push_back(e);}return ret;}//先排序,让相同的挨在一起sort(nums.begin(), nums.end());//通过左邻右舍 来判断是否形单影只for (int i = 0; i < sz; i++) {if (i == 0 && nums[i] != nums[i + 1]) {ret.push_back(nums[i]);}else if (i == sz - 1 && nums[i] != nums[i - 1]) {ret.push_back(nums[i]);}else if (i>0 && i<sz-1&&nums[i] != nums[i - 1] && nums[i] != nums[i + 1]) {{ret.push_back(nums[i]);}}}return ret;}
};
我的错误记录:
我一开始,在if else的条件上出了bug
for (int i = 0; i < sz; i++) {if (i == 0 && nums[i] != nums[i + 1]) {ret.push_back(nums[i]);}else if (i == sz - 1 && nums[i] != nums[i - 1]) {ret.push_back(nums[i]);}else{if(nums[i] != nums[i - 1] && nums[i] != nums[i + 1]){ret.push_back(nums[i]);}}
}

出了bug不要怕,我们来看看它的报错内容:vector subscript out of range(subscript“下标”,数组下标超出范围)
经过检查发现:
当i=0时,它走不了前两条if。由于第三个else没设条件判断的门槛,所以i=0直接就进入了,进去以后,i-1导致下标越界。
所以说,if else语句的条件判断要多加小心!
思路二:位运算
(假设那俩不相等的数为a、b)
Step 1.先将所有数字异或在一起,得到一个非0的值ret。
为什么ret一定非0呢?因为只有当所有数字都是成对相同的出现时,ret才会为0,而这里明确了有两个不相等的数字。
因为相等的数异或 会抵消为0,所以这个ret就是a和b异或的值。
Step 2.假设得到的ret是101000,那为1的比特位 就是一道“分水岭”,因为这个比特位上,一定是0和1异或在一起,才会得到1。
所以,我们可以找到ret中最低位的那个1,这个比特位把数组元素分为两大阵营:组A. 此比特位为0 ,组B. 此比特位为1。
Step 3. 组A内的所有元素异或在一起,得到a;组B内的所有元素异或在一起,得到b。
class Solution {
public:vector<int> singleNumber(vector<int>& nums) {int ret=0;for(int e:nums){ret^=e;}//找到为1的最低比特位int i=0;for(i=0;i<32;i++){if((ret>>i)&1==1){break;}}//分组int group1_ret=0,group2_ret=0;for(int e:nums){if((e>>i)&1==1){ //该比特位为1的为group1group1_ret^=e;}else{ //该比特位为1的为group2group2_ret^=e;}}return {group1_ret,group2_ret}; }
};
电话号码的字母组合
力扣(LeetCode)官网 - 全球极客挚爱的技术成长平台
给定一个仅包含数字 2-9 的字符串,返回所有它能表示的字母组合。答案可以按 任意顺序 返回。
给出数字到字母的映射如下(与电话按键相同)。注意 1 不对应任何字母。

示例 1:
输入:digits = "23"
输出:["ad","ae","af","bd","be","bf","cd","ce","cf"]
示例 2:
输入:digits = ""
输出:[]
示例 3:
输入:digits = "2"
输出:["a","b","c"]
思路
假设digits="23",我们把2、3视为“一层”:

遍历每一层,用n次递归的方式。
遍历一层中的每一个元素,用范围for。
class Solution {
public:string num_to_str[10]={"","","abc","def","ghi","jkl","mno","pqrs","tuv","wxyz"};
void combine_letter(string digits,int di,string unit_ret,vector<string>& ret){if(di==digits.size()){ret.push_back(unit_ret); //每一层访问完毕,得出一个unit_ret return; }int n=digits[di]-'0';string str=num_to_str[n];for(auto c:str){combine_letter(digits,di+1,unit_ret+c,ret); //访问下一层}}vector<string> letterCombinations(string digits) {vector<string> ret;string unit_ret;if(digits==""){ //先考虑特殊情况return ret;}combine_letter(digits,0,unit_ret,ret);return ret; }
};
注意:1.要将数组num_to_str设为类域里的全局变量,这样函数combine_letter就能直接访问了。
我一开始把数组num_to_str写在函数letterCombinations里,并用static修饰,使之成为静态的局部变量。
然而,我弄混了,静态的局部变量并不会改变它的作用域,只是使它的生命周期变长了。
static局部变量出作用域不会被销毁,但是别的函数是没法访问到它的,它的作用域不变。
正确的做法是写在letterCombinations外,使之称为(类域里的)全局变量。
失败记录
虽然我知道,能用递归写的循环也能写,但这道题我还是不会循环的写法,花了好多时间……
用递归的好处是能把复杂的大事 转化成 好解决的小事。
第一次没写出来,我就去看题解。结果递归那一块老是不懂,好晕。这时,最好的办法是,打开IDE,把代码拷进去,自己调试时走一遍代码,就能理解透了:

现在我们来梳理下这个递归:
➡️一开始错误的认知:(假设digits==“23”):
我以为,先是找到2对应的a,给a开个栈帧,在此栈帧里找到3对应的d,给d开栈帧,然后再开新栈帧;最后,新栈帧、d的栈帧、a的栈帧逐一销毁。
再开b的栈帧……

➡️正确的认知:
而实际上,开新栈帧的因素是di。di==0时,开栈帧1号;在栈帧1号里,di ==1,开栈帧2号;在栈帧2号里,di ==2,开栈帧3号。
然后,3号销毁,而2号并不会随之销毁。2号栈帧里要完成对def三个字母的遍历,所以,会开3次栈帧3号。
当def三个字母都完成啦遍历,栈帧2号才会销毁,此时回到栈帧1号。
栈帧1号同样要完成abc三个字母的遍历,才会销毁。所以,一共开3次栈帧2号,每个栈帧2号里又要开3次栈帧3号,一共开9次栈帧3号。

要注意的细节
➡️1.注意区分+和+= !
+:用来计算两个数值的和,计算结束后会产生一个新的值。
+=:用来计算两个数值的和,计算结果会赋值给+=运算符前的参数。
拿这里来举例:
for(auto c:str){combine_letter(digits,di+1,unit_ret+c,ret);
}
写法一:unit_ret+c的结果 作为新的unit_ret参数,传给下一个调用的combine_letter函数,而实际上,unit_ret的值并未被改变。
如果写成这样,就错了:
for(auto c:str){unit_ret+=c; //写法二combine_letter(digits,di+1,unit_ret,ret);
}
写法二:unit_ret+c的结果会赋给unit_ret,拷贝unit_ret的值作为形参,传给下一个调用的combine_letter函数。unit_ret的值被改变。
➡️2.unit_ret注意是传值传参!不能传引用传参。
void combine_letter(string digits,int di,string unit_ret,vector<string>& ret);
为什么不能传引用传参呢?
如果传引用过去,那在这一步里,unit_ret每次加的c,都会保留下来。而如果传值传参,每个栈帧里的unit_ret都是拷贝出来的值,当栈帧销毁,拷贝的unit_ret也就销毁了,而实际的unit_ret不受影响。
for(auto c:str){combine_letter(digits,di+1,unit_ret+c,ret); //访问下一层
}
相关文章:
【vector题解】只出现一次的数字 | 电话号码的数字组合
只出现一次的数字 力扣(LeetCode)官网 - 全球极客挚爱的技术成长平台 给你一个整数数组 nums,其中恰好有两个元素只出现一次,其余所有元素均出现两次。 找出只出现一次的那两个元素。你可以按 任意顺序 返回答案。 你必须设计并…...
VS2022 开发方式
使用 C# 在VS 2022 上开发时,发现有多种项目类型可以创建。这些类型放一起容易搞混,于是记录一下各种类型的区别。 这里主要介绍windows控制台程序、MFC程序、WPF程序、WinForm程序的特点。 创建哪种应用? 创建控制台应用 Windows控制台程序…...
【Python语言速回顾】——数据可视化基础
目录 引入 一、Matplotlib模块(常用) 1、绘图流程&常用图 编辑 2、绘制子图&添加标注 编辑 3、面向对象画图 4、Pylab模块应用 二、Seaborn模块(常用) 1、常用图 2、代码示例 编辑 编辑 编辑 …...
java实现pdf文件添加水印,下载到浏览器
java实现pdf文件添加水印,下载到浏览器 添加itextpdf依赖 <dependency><groupId>com.itextpdf</groupId><artifactId>itextpdf</artifactId><version>5.5.8</version> </dependency>文件下载到浏览器和指定路径 …...
代码随想录算法训练营第四十一天丨 动态规划part04
01背包理论基础 见连接:代码随想录 416. 分割等和子集 思路 01背包问题 背包问题,大家都知道,有N件物品和一个最多能背重量为W 的背包。第i件物品的重量是weight[i],得到的价值是value[i] 。每件物品只能用一次,求解…...
PyCharm免费安装和新手使用教程
简介 PyCharm是一款由JetBrains公司开发的Python集成开发环境(IDE)。它提供了一系列强大的功能,包括自动代码完成、语法高亮、自动缩进、代码重构、调试器、测试工具、版本控制工具等,使开发者可以更加高效地开发Python应用程序。…...
使用Python的Scikit-Learn进行决策树建模和可视化:以隐形眼镜数据集为例
决策树是一种强大的机器学习算法,它在数据挖掘和模式识别中被广泛应用。决策树模型可以帮助我们理解数据中的模式和规则,并做出预测。在本文中,我们将介绍如何使用Python的Scikit-Learn库构建决策树模型,并使用Graphviz进行可视化…...
开源软件:释放创新的力量,改变数字世界的游戏规则
在充满活力的技术领域,创新是至高无上的,有一种方法已获得显著的吸引力——开源软件。开源软件凭借其透明、协作和无限可能性的精神,彻底改变了我们开发、共享和定制应用程序的方式。从操作系统到数据分析工具,其影响跨越了多个领…...
【QT】鼠标常用事件
新建项目 加标签控件 当鼠标进去,显示【鼠标进入】,离开时显示【鼠标离开】 将QLable提升成自己的控件,然后再去捕获 添加文件 改继承的类名 提升类 同一个父类,可以提升 效果 现在代码就和Qlabel对应起来了。 在.h中声明&…...
LuatOS-SOC接口文档(air780E)--mlx90640 - 红外测温(MLX90640)
常量# 常量 类型 解释 mlx90640.FPS1HZ number FPS1HZ mlx90640.FPS2HZ number FPS2HZ mlx90640.FPS4HZ number FPS4HZ mlx90640.FPS8HZ number FPS8HZ mlx90640.FPS16HZ number FPS16HZ mlx90640.FPS32HZ number FPS32HZ mlx90640.FPS64HZ number FPS6…...
java连接本地数据库可以简写为///
java连接数据库配置文件写为: server:port: 8091 spring:application:name: user-managerdatasource:driver-class-name: com.mysql.cj.jdbc.Driverurl: jdbc:mysql://localhost:3306/user?serverTimezoneAsia/Shanghai&characterEncodingutf-8username: root…...
基于springboot漫画动漫网站
基于springbootvue漫画动漫网站 摘要 基于Spring Boot的漫画动漫网站是一个精彩的项目,它结合了现代Web开发技术和漫画爱好者的热情。这个网站的目标是为用户提供一个便捷的平台,让他们能够欣赏各种漫画和动漫作品,与其他爱好者分享他们的兴趣…...
autoFac 生命周期 试验
1.概述 autoFac的生命周期 序号名称说明1InstancePerDependency每次请求都创建一个新的对象2InstancePerLifetimeScope同一个Lifetime生成的对象是同一个实例3SingleInstance每次都用同一个对象 2.注 InstancePerLifetimeScope 同一个Lifetime生成的对象是同一个实例&#x…...
foreach、for in 和for of的区别?
forEach,for...in 和 for...of 是 JavaScript 中用于遍历数据的三种不同的结构。它们在遍历数组、对象和可迭代对象(如 Set 和 Map)时非常有用。尽管它们都可以用于循环遍历,但它们之间存在一些重要的区别: forEach&a…...
【Effective C++】条款45: 运用成员函数模板接受所有兼容的类型
假设有如下继承结构: class Top{}; class Middle: public Top{}; class Bottom: public Middle{};public继承意味着is-a关系,所有的基类都是派生类,但反之则不是,例如所有的学生都是人,但不是所有的人都是学生. 派生类到基类的指针可以直接隐式转换 Top* pt1 new Middle; T…...
WSL1 安装 debian xfce 用xrdp 导入远程桌面
凑合能用 晃晃行 晃晃不行 而且比较卡 还经常报崩溃 sudo apt install xfce4 xfce4-goodies xorg dbus-x11 x11-xserver-utils apt install locales -y 安装过完应该会提示设置locales,如果安装完之后想要更改相关设置,可以使用如下命令重新设置loca…...
WPF RelativeSource属性-目标对象类型易错
上一篇转载了RelativeSource的三种用法,其中第二种用法较常见,这里记录一下项目中曾经发生错误的地方,以防自己哪天忘记了,又犯了同样错误—WPF RelativeSource属性-CSDN博客 先回顾一下: 控件关联其父级容器的属性—…...
Java while 和do while 循环
循环是程序中的重要流程结构之一。循环语句能够使程序代码重复执行,适用于需要重复一段代码直到满足特定条件为止的情况。 所有流行的编程语言中都有循环语句。Java 中采用的循环语句与C语言中的循环语句相似,主要有 while、do-while 和 for。 另外 Ja…...
应用软件安全编程--03净化传递给 Runtime.exec() 方法的非受信数据
每个 Java 应用都有一个 Runtime 类的实例, 一般需要使用 shell 时调用它,从而可以在 POSIX 中 使用/bin/sh 或者在Windows 平台中使用cmd.exe。 当参数中包含以空格、双引号或者其他以一/开头 的用来表示分支的字符时,就可能发生参数注入攻…...
uniapp阻止冒泡的方法,点击事件嵌套点击事件,怎么阻止同时触发
uniapp阻止冒泡的方法 当我们遇到点击事件嵌套点击事件的时候,点击里边的事件,外边的也会跟着触发该怎么办? 起初我尝试用了css里的修改z-index属性的方法,把里边的<view>标签放在上边,结果两个事件还是同时触发…...
synchronized 学习
学习源: https://www.bilibili.com/video/BV1aJ411V763?spm_id_from333.788.videopod.episodes&vd_source32e1c41a9370911ab06d12fbc36c4ebc 1.应用场景 不超卖,也要考虑性能问题(场景) 2.常见面试问题: sync出…...
树莓派超全系列教程文档--(62)使用rpicam-app通过网络流式传输视频
使用rpicam-app通过网络流式传输视频 使用 rpicam-app 通过网络流式传输视频UDPTCPRTSPlibavGStreamerRTPlibcamerasrc GStreamer 元素 文章来源: http://raspberry.dns8844.cn/documentation 原文网址 使用 rpicam-app 通过网络流式传输视频 本节介绍来自 rpica…...
K8S认证|CKS题库+答案| 11. AppArmor
目录 11. AppArmor 免费获取并激活 CKA_v1.31_模拟系统 题目 开始操作: 1)、切换集群 2)、切换节点 3)、切换到 apparmor 的目录 4)、执行 apparmor 策略模块 5)、修改 pod 文件 6)、…...
三维GIS开发cesium智慧地铁教程(5)Cesium相机控制
一、环境搭建 <script src"../cesium1.99/Build/Cesium/Cesium.js"></script> <link rel"stylesheet" href"../cesium1.99/Build/Cesium/Widgets/widgets.css"> 关键配置点: 路径验证:确保相对路径.…...
el-switch文字内置
el-switch文字内置 效果 vue <div style"color:#ffffff;font-size:14px;float:left;margin-bottom:5px;margin-right:5px;">自动加载</div> <el-switch v-model"value" active-color"#3E99FB" inactive-color"#DCDFE6"…...
python如何将word的doc另存为docx
将 DOCX 文件另存为 DOCX 格式(Python 实现) 在 Python 中,你可以使用 python-docx 库来操作 Word 文档。不过需要注意的是,.doc 是旧的 Word 格式,而 .docx 是新的基于 XML 的格式。python-docx 只能处理 .docx 格式…...
EtherNet/IP转DeviceNet协议网关详解
一,设备主要功能 疆鸿智能JH-DVN-EIP本产品是自主研发的一款EtherNet/IP从站功能的通讯网关。该产品主要功能是连接DeviceNet总线和EtherNet/IP网络,本网关连接到EtherNet/IP总线中做为从站使用,连接到DeviceNet总线中做为从站使用。 在自动…...
今日科技热点速览
🔥 今日科技热点速览 🎮 任天堂Switch 2 正式发售 任天堂新一代游戏主机 Switch 2 今日正式上线发售,主打更强图形性能与沉浸式体验,支持多模态交互,受到全球玩家热捧 。 🤖 人工智能持续突破 DeepSeek-R1&…...
AI书签管理工具开发全记录(十九):嵌入资源处理
1.前言 📝 在上一篇文章中,我们完成了书签的导入导出功能。本篇文章我们研究如何处理嵌入资源,方便后续将资源打包到一个可执行文件中。 2.embed介绍 🎯 Go 1.16 引入了革命性的 embed 包,彻底改变了静态资源管理的…...
企业如何增强终端安全?
在数字化转型加速的今天,企业的业务运行越来越依赖于终端设备。从员工的笔记本电脑、智能手机,到工厂里的物联网设备、智能传感器,这些终端构成了企业与外部世界连接的 “神经末梢”。然而,随着远程办公的常态化和设备接入的爆炸式…...
