面试经典150题:数组/字符串合集
新专栏,预计两个月写完吧,每天下班回来抽空做几道题。会把做题计划顺序记录下来,如果你有缘,刷到这个开篇序列,那就跟着文章去练题吧。初学者可以慢慢来
88. 合并两个有序数组
void merge(vector<int>& nums1, int m, vector<int>& nums2, int n) {int i=m-1;int j=n-1;int k=m+n-1;//从后往前插while(j>=0){if(i>=0&&nums1[i]>nums2[j]){nums1[k--]=nums1[i];i--;}else{nums1[k--]=nums2[j];j--;}}}
27. 移除元素
这是前后指针覆盖做的,也可以双向指针交换做,思路 i从0开始,j从尾巴开始,如果i的值不等于val那就++,如果等于了就和j的值交换,j--,i不变,下一轮再交换来的i还是不是val,是的话继续交换,j--,这样循环
int removeElement(vector<int>& nums, int val) {int i=0,j=0;while(j<nums.size()){if(nums[j]!=val){nums[i]=nums[j];j++;i++;}else{j++;}}return i;}
26. 删除有序数组中的重复项
int removeDuplicates(vector<int>& nums) {int i=0,j=0;while(j<nums.size()){if(nums[i]==nums[j]){j++;}else{++i;nums[i]=nums[j];j++;}}return i+1;}
80. 删除有序数组中的重复项 II
int removeDuplicates(vector<int>& nums) {int i=0,j=0;while(j<nums.size()){if(i<2||nums[j]!=nums[i-2]){nums[i++]=nums[j];}j++;}return i;}
169. 多数元素
方法太多了,我写三个就行
int majorityElement(vector<int>& nums) {sort(nums.begin(),nums.end());return nums[nums.size()/2];}int majorityElement(vector<int>& nums) {unordered_map<int,int>mp;int ans=0;for(const auto &x:nums){mp[x]++;if(mp[x]>nums.size()/2){ans=x;}}return ans;}摩尔投票法只满足超过一半的投票,符合题意玩的就是票数抵消,留下存活的那个int majorityElement(vector<int>& nums) {//摩尔投票法,一种很奇妙的思路int candition=0;//候选人int vote=0;//票数for(auto x:nums){if(vote==0)candition=x;if(x==candition)vote++;if(x!=candition)vote--;}return candition;}
189. 轮转数组
第一句为了防止越界,这力扣限制服了,,写了两种方法
void rotate(vector<int>& nums, int k) {k%=nums.size();vector<int>vv;vv.reserve(nums.size()*2);vv.insert(vv.end(),nums.begin(),nums.end());vv.insert(vv.end(),nums.begin(),nums.end());vector<int>vp(vv.begin()+nums.size()-k,vv.begin()+nums.size()*2-k);nums=vp;}void rotate(vector<int>& nums, int k) {k%=nums.size();reverse(nums.begin(),nums.begin()+nums.size()-k);reverse(nums.begin()+nums.size()-k,nums.end());reverse(nums.begin(),nums.end());}
121. 买卖股票的最佳时机
int maxProfit(vector<int>& prices) {vector<vector<int>>dp(prices.size(),vector<int>(2));dp[0][0]=-prices[0]; //有股票dp[0][1]=0; //没有股票for(int i=1;i<prices.size();++i){dp[i][0]=max(-prices[i],dp[i-1][0]);dp[i][1]=max(dp[i-1][1],dp[i-1][0]+prices[i]);}return dp[prices.size()-1][1];}
122. 买卖股票的最佳时机 II
int maxProfit(vector<int>& prices) {//0 手里没股票 ,1手里有股票vector<vector<int>>dp(prices.size(),vector<int>(2));dp[0][0]=0;dp[0][1]=-prices[0];for(int i=1;i<prices.size();++i){dp[i][1]=max(dp[i-1][0]-prices[i],dp[i-1][1]);dp[i][0]=max(dp[i-1][0],dp[i-1][1]+prices[i]);}return dp[prices.size()-1][0];}
55. 跳跃游戏
只要范围覆盖能到就行
bool canJump(vector<int>& nums) {int n=nums.size()-1;int cover=0;for(int i=0;i<=cover;++i){cover=max(nums[i]+i,cover);if(cover>=n){return true;}}return false;}
45.跳跃游戏2
int jump(vector<int>& nums) {if(nums.size()==1){return 0;}int n=nums.size()-1;int cover=0;int ans=0;int cur=0;for(int i=0;i<nums.size();++i){cover=max(i+nums[i],cover);if(i==cur){ans++;cur=cover;if(cover>=n){break;}}}return ans;}
274. H 指数
int hIndex(vector<int>& citations) {//默认h为文章数,对引用量排序,如果小于h,将h--。int lens=citations.size();if(lens==0){return 0;}int h=lens;sort(citations.begin(),citations.end());for(auto x:citations){if(x<h){h--;}}return h;}
380. O(1) 时间插入、删除和获取随机元素
用vector的下标和map做映射
class RandomizedSet {
private:vector<int>vv;unordered_map<int,int>mp; //key->val vaule->index
public:RandomizedSet() {srand((unsigned int)time(NULL));}bool insert(int val) {if(mp.count(val)){return false;}int idx=vv.size();mp[val]=idx;vv.push_back(val);return true;}bool remove(int val) {if(!mp.count(val)){return false;}int preidx=mp[val];int curidx=vv.size()-1;vv[preidx]=vv[curidx];//更新map 对应下标mp[vv[preidx]]=preidx;//删除vv.pop_back();mp.erase(val);return true;}int getRandom() {int idx=rand()%vv.size();return vv[idx];}
};
238. 除自身以外数组的乘积
vector<int> productExceptSelf(vector<int>& nums) {//左乘积 * 右乘积int ml=1;vector<int>vv(nums.size(),1);for(int i=1;i<nums.size();++i){ml*=nums[i-1];vv[i]=ml;}int mr=1;for(int i=nums.size()-2;i>=0;--i){mr*=nums[i+1];vv[i]*=mr;}return vv;}
134.加油站
int canCompleteCircuit(vector<int>& gas, vector<int>& cost) {/* if(accumulate(gas.begin(),gas.end(),0)<accumulate(cost.begin(),cost.end(),0)){return -1;}*///不要上面那句就加一个total 记录完整一路看有没有剩油int total=0;int cur=0;int index=0;for(int i=0;i<gas.size();++i){total+=gas[i]-cost[i];cur+=gas[i]-cost[i];if(cur<0){index=i+1;cur=0;}} return total<0?-1:index;}
135. 分发糖果
int candy(vector<int>& ratings) {//每个孩子都至少有一个糖果vector<int>res(ratings.size(),1);//从前往后,把右边分数高的糖果多一个for(int i=0;i<ratings.size()-1;++i){if(ratings[i]<ratings[i+1]){res[i+1]=res[i]+1;}}//从后往前,把左边分数高的糖果多分一个//局部还要贪心,要给第i个孩子分当前糖果和右边糖果数+1的最大值//给到当前孩子糖果,因为这样才能保证局部此时第i个孩子的糖果,比左边右边相邻都大//体现到全局就是每每相邻的两个孩子,分数最大的那个一定糖果最多for(int i=ratings.size()-1;i>0;--i){if(ratings[i-1]>ratings[i]){res[i-1]=max(res[i-1],res[i]+1);}}return accumulate(res.begin(),res.end(),0);}
42. 接雨水
我有篇博客详细讲了这个题的做法,用了五种方法
这块我演示三种推荐的
找到最高点,左右两边,求雨水
int trap(vector<int>& height) {int ans=0;int value=0;int index=0;for(int i=0;i<height.size();++i){if(height[i]>value){value=height[i];index=i;}}int st=0;for(int i=0;i<index;++i){if(height[i]>st){st=height[i];}else{ans+=st-height[i];}}st=0;for(int i=height.size()-1;i>index;--i){if(height[i]>st){st=height[i];}else{ans+=st-height[i];}}return ans;}
双指针
int trap(vector<int>& height) {int left=0;int right=height.size()-1;int ans=0;int mlhi=height[0];int rlhi=height[height.size()-1];while(left<right){mlhi=max(mlhi,height[left]);rlhi=max(rlhi,height[right]);if(mlhi>rlhi){ans+=rlhi-height[right];right--;}else{ans+=mlhi-height[left];left++;}}return ans;}
单调栈 递减
int trap(vector<int>& height) {stack<int>sk;sk.push(0);int ans=0;for(int i=1;i<height.size();++i){while(!sk.empty()&&height[i]>height[sk.top()]){int righthright=height[i];int curheight=height[sk.top()];sk.pop();if(!sk.empty()){int leftheight=height[sk.top()];int chang=i-sk.top()-1;int gao=min(righthright,leftheight)-curheight;ans+=chang*gao;}}sk.push(i);}return ans;}
13. 罗马数字转整数
int romanToInt(string s) {int res=0;for(int i=0;i<s.size();++i){if(s[i]=='V')res+=5;else if(s[i]=='L')res+=50;else if(s[i]=='D')res+=500;else if(s[i]=='M')res+=1000;else if(s[i]=='I'){ //一点代码技巧res=s[i+1]=='V'||s[i+1]=='X'?res-1:res+1;}else if(s[i]=='X'){res=s[i+1]=='L'||s[i+1]=='C'?res-10:res+10;}else{res=s[i+1]=='D'||s[i+1]=='M'?res-100:res+100;}}return res;}
12.整数转罗马数字
string intToRoman(int num) {//哈希int arr[]{1000,900,500,400,100,90,50,40,10,9,5,4,1};string btr[]{"M","CM","D","CD","C","XC","L","XL","X","IX","V","IV","I"};string ans="";for(int i=0;i<sizeof(arr)/sizeof(arr[0]);++i){while(num>=arr[i]){num-=arr[i];ans+=btr[i];}}return ans;}
58. 最后一个单词的长度
int lengthOfLastWord(string s) {int count=0;int i=s.size()-1;for(i;i>=0;){if(count&&s[i]==' '){break;}if(s[i]==' '){i--;}else{count++;i--;}}return count;}
14. 最长公共前缀
学习minmax_element
string longestCommonPrefix(vector<string>& strs) {if(strs.empty())return "";auto p=minmax_element(strs.begin(),strs.end());for(int i=0;i<p.first->size();++i){if(p.first->at(i)!=p.second->at(i)){return p.first->substr(0,i);}}return *p.first;}
string longestCommonPrefix(vector<string>& strs) {//纵向对比,横向去扫描//abcf//ab//absif(strs.empty()){return "";}string res="";for(int j=0;j<strs[0].size();++j){for(int i=0;i<strs.size();++i){if(strs[0][j]!=strs[i][j]){return res;} }res+=strs[0][j];}return res;}
151. 反转字符串中的单词
直接重构字符串,,不用erase去写了,erase版本好麻烦写起来
string reverseWords(string s) {//重构字符串,去重多余空格int slow=0;for(int i=0;i<s.size();++i){if(s[i]!=' '){if(slow!=0) //处理中间,只放一个空格{s[slow++]=' ';} while(s[i]!=' '&&i<s.size()){s[slow++]=s[i++];}}}s.resize(slow);int j=0;for(int i=0;i<s.size();++i){if(s[i]==' '){reverse(s.begin()+j,s.begin()+i);j=i+1;}}reverse(s.begin()+j,s.end());reverse(s.begin(),s.end());return s;}
6. N 字形变换
string convert(string s, int numRows) {string res="";if(numRows==1)return s;vector<string>vv(numRows);int k=0;int flg=1;//标志转向for(int i=0;i<s.size();++i){vv[k]+=s[i];if(k==0||k==numRows-1){flg*=-1;}k+=flg>0?-1:1;}for(auto x:vv){res+=x;}return res;}
28. 找出字符串中第一个匹配项的下标
要用kmp。麻烦,
暴力解法:
int strStr(string haystack, string needle) {if(haystack.size()<needle.size()){return -1;}int index=INT_MAX;int k=0;for(int i=0;i<haystack.size();++i){for(int j=i;j<haystack.size();++j){if(haystack[j]==needle[k]){k++;if(k==needle.size()){index=i;return i;}}else{k=0;break;}}}return -1;}
kmp: 面试的时候要是面试官让你去写kmp,就把屎盆子扣他脑门,,看着代码感觉不多,思想是极其巧妙的,很难理解,而且稍微一变形,你会难的你根本不知道用kmp从何下手,Knuth-Morris-Pratt 三兄弟,花了若干年研究的成果,在网上各路大神眼里,居然是个简单算法。。。
总之除非你把kmp理解的非常非常清楚,随便一个类型题就就能在15分钟内靠理解的kmp搞出来,那你可以去申请图灵奖了
反正我是每次写到这题就是暴力,然后看看kmp题解,看懂一次 过几天就忘了
void ex(int *arr,const string&needle){int j=0;arr[0]=j;for(int i=1;i<needle.size();++i){while(j>0&&needle[j]!=needle[i]){j=arr[j-1];}if(needle[i]==needle[j]){j++;}arr[i]=j;}}int strStr(string haystack, string needle) {if(needle.size()==0){return -1;}int arr[needle.size()];ex(arr,needle);int j=0;for(int i=0;i<haystack.size();++i){while(j>0&&haystack[i]!=needle[j]) //回退{j=arr[j-1];}if(haystack[i]==needle[j]){j++;}if(j==needle.size()){return i-needle.size()+1;}}return -1;}
相关文章:
面试经典150题:数组/字符串合集
新专栏,预计两个月写完吧,每天下班回来抽空做几道题。会把做题计划顺序记录下来,如果你有缘,刷到这个开篇序列,那就跟着文章去练题吧。初学者可以慢慢来 88. 合并两个有序数组 void merge(vector<int>& nums…...
Java源文件的执行过程
目录 1.JVM 2.字节码 3.Java源文件执行的过程 4.JIT(Just In Time Compilation) 5.AOT(Ahead Of Time Compilation) 6.AOT破坏Java动态性 7.编译型语言与解释型语言 8.Java-编译与解释并存的语言 9.Java和C的相同点与不同…...

10个ai算法常用库java版
今年ChatGPT 火了半年多,热度丝毫没有降下来。深度学习和 NLP 也重新回到了大家的视线中。有一些小伙伴问我,作为一名 Java 开发人员,如何入门人工智能,是时候拿出压箱底的私藏的学习AI的 Java 库来介绍给大家。 这些库和框架为机器学习、深度学习、自然语言处理等提供了广…...
怎么看服务器带宽大小 103.219.179.X
第一种,可以使用网站测速,这种方式比较便捷,但是由于网站测速是测试服务器发送数据包到他网站节点的一个速度情况,有时候节点问题或者服务器做了封包限制可能导致测试不准确的情况。 第二种,可以在IIS上架设一个大一点…...

图形编辑器开发:最基础但却复杂的选择工具
大家好,我是前端西瓜哥。 对于一个图形设计软件,它最基础的工具是什么?选择工具。 但这个选择工具,却是相当的复杂。这次我来和各位,细说细说选择工具的一些弯弯道道。 我正在开发的图形设计工具的: http…...
apk签名-signapk.jar
如果做平台app开发,需要签platform签名,除了通过adroid.bp或者android.mk的方式使用AOSP整个大工程中签名外,还可以直接通过signapk.jar的方式进行签名,效率更高更快捷简便。 首先我们来回顾下AOSP平台签名的办法。 Android.mk 使…...

【100个高大尚求职简历】简历模板+修改教程+行业分类简历模板 (涵盖各种行业) (简历模板+编辑指导+修改教程)
文章目录 1 简历预览2 简历下载 很多人说自己明明投了很多公司的简历,但是都没有得到面试邀请的机会。自己工作履历挺好的,但是为什么投自己感兴趣公司的简历,都没有面试邀请的机会。反而是那些自己没有投递的公司,经常给自己打电…...
Nginx平滑升级版本或添加模块
文章目录 一、Nginx 平滑升级二、升级失败 回滚操作三、遇到问题 一、Nginx 平滑升级 一般有两种情况下需要升级 nginx,一种是确实要升级 nginx 的版本,另一种是要为 nginx 添加新的模块。 Nginx平滑升级其原理简单概括: (1&am…...

高阶复杂网络重建:从时间序列中重建高阶网络
论文链接:https://www.nature.com/articles/s41467-022-30706-9 一、为什么要研究高阶网络? 复杂网络跟我们生活息息相关,例如社交网络的信息传播,疾病的感染扩散和基因调控网络的相互作用等。越来越多的研究突破了传统网络中两…...

Day05 03-MySQL主从-主主原理与搭建详解
文章目录 第十六章 MySQL的系统架构(主从架构)16.1 MySQL集群架构的介绍16.1.1 主从架构介绍16.1.2 主从复制的原理 16.2 MySQL主从复制的实现16.2.1 环境说明16.2.2 主库配置16.2.3 从库配置16.2.4 主从复制测试 16.3 MySQL主主复制的实现16.3.1 主主复…...

STL之vector
目录 vector模拟实现一. vector的基本框架二. 常用方法及实现1.初始化和清理a. 默认构造函数b. 析构函数 2. 迭代器a. beginb. end 3.数据访问a. sizeb. capacityc. operator[]d. frontc. back 4.增删查改操作a. reserveb. resizec. insertd. push_backe. erasef. pop_back 5.构…...

2020年CSP-J认证 CCF非专业级别软件能力认证第一轮真题-单项选择题解析
2020 CCF认证第一轮(CSP-J)真题 一、单项选择题 (共15题,每2分,共30分;每题有且有一个正确选项) 1、在内存储器中每个存储单元都被赋予一个唯一的序号,称为 A、下标 B、序号 C、地址 D、编号 答案:C…...

vscode Delete `␍⏎·····`
在公司拉取代码报错 Delete ␍⏎,首先问题的关键是换行导致,相信你看别的博客也知道为什么了,但是我使用别的博客的解决办法,没搞定,无论是配置 auto 还是命令行执行,都不行 下面介绍我的解决办法 我使用…...

读书笔记-《ON JAVA 中文版》-摘要16[第十六章 代码校验]
文章目录 第十六章 代码校验1. 测试1.1 单元测试1.2 JUnit1.3 测试覆盖率的幻觉 2. 前置条件2.1 断言(Assertions)2.2 Java 断言语法2.3 Guava 断言2.4 使用断言进行契约式设计2.4.1 检查指令2.4.2 前置条件2.4.3 后置条件2.4.4 不变性2.4.5 放松 DbC 检…...
SQL Server:打造高效数据管理系统的利器
使用SQL Server进行数据管理 简介 SQL Server是由Microsoft开发的一款关系型数据库管理系统,它可以用于存储和管理大量结构化数据。本篇博客将介绍如何使用SQL Server进行数据管理。 数据库连接 在开始使用SQL Server之前,需要先建立与数据库的连接。…...
代码随想录二刷day20 | 二叉树之 654.最大二叉树 617.合并二叉树 700.二叉搜索树中的搜索 98.验证二叉搜索树
day20 654.最大二叉树617.合并二叉树700.二叉搜索树中的搜索98.验证二叉搜索树 654.最大二叉树 题目链接 解题思路: 本题属于构造二叉树,需要使用前序遍历,因为先构造中间节点,然后递归构造左子树和右子树。 确定递归函数的参数…...

python基础知识(十三):numpy库的基本用法
目录 1. numpy的介绍2. numpy库产生矩阵2.1 numpy将列表转换成矩阵2.2 numpy创建矩阵 3. numpy的基础运算4. numpy的基础运算25. 索引 1. numpy的介绍 numpy库是numpy是python中基于数组对象的科学计算库。 2. numpy库产生矩阵 2.1 numpy将列表转换成矩阵 import numpy as …...
【SA8295P 源码分析】16 - TouchScreen Panel (TP)线程函数 tp_recv_thread() 源码分析
【【SA8295P 源码分析】16 - TouchScreen Panel (TP)线程函数 tp_recv_thread 源码分析 一、TP 线程函数:tp_recv_thread()二、处理&上报 坐标数据 cypress_read_touch_data()系列文章汇总见:《【SA8295P 源码分析】00 - 系列文章链接汇总》 本文链接:《【SA8295P 源码…...

Python3数据分析与挖掘建模(13)复合分析-因子关分析与小结
1.因子分析 1.1 探索性因子分析 探索性因子分析(Exploratory Factor Analysis,EFA)是一种统计方法,用于分析观测变量之间的潜在结构和关联性。它旨在确定多个观测变量是否可以归结为较少数量的潜在因子,从而帮助简化…...

【stable diffusion】图片批量自动打标签、标签批量修改(BLIP、wd14)用于训练SD或者LORA模型
参考: B站教学视频【:AI绘画】新手向!Lora训练!训练集准备、tag心得、批量编辑、正则化准备】官方教程:https://github.com/darkstorm2150/sd-scripts/blob/main/docs/train_README-en.md#automatic-captioning 一、…...
进程地址空间(比特课总结)
一、进程地址空间 1. 环境变量 1 )⽤户级环境变量与系统级环境变量 全局属性:环境变量具有全局属性,会被⼦进程继承。例如当bash启动⼦进程时,环 境变量会⾃动传递给⼦进程。 本地变量限制:本地变量只在当前进程(ba…...
脑机新手指南(八):OpenBCI_GUI:从环境搭建到数据可视化(下)
一、数据处理与分析实战 (一)实时滤波与参数调整 基础滤波操作 60Hz 工频滤波:勾选界面右侧 “60Hz” 复选框,可有效抑制电网干扰(适用于北美地区,欧洲用户可调整为 50Hz)。 平滑处理&…...
工程地质软件市场:发展现状、趋势与策略建议
一、引言 在工程建设领域,准确把握地质条件是确保项目顺利推进和安全运营的关键。工程地质软件作为处理、分析、模拟和展示工程地质数据的重要工具,正发挥着日益重要的作用。它凭借强大的数据处理能力、三维建模功能、空间分析工具和可视化展示手段&…...
oracle与MySQL数据库之间数据同步的技术要点
Oracle与MySQL数据库之间的数据同步是一个涉及多个技术要点的复杂任务。由于Oracle和MySQL的架构差异,它们的数据同步要求既要保持数据的准确性和一致性,又要处理好性能问题。以下是一些主要的技术要点: 数据结构差异 数据类型差异ÿ…...

现代密码学 | 椭圆曲线密码学—附py代码
Elliptic Curve Cryptography 椭圆曲线密码学(ECC)是一种基于有限域上椭圆曲线数学特性的公钥加密技术。其核心原理涉及椭圆曲线的代数性质、离散对数问题以及有限域上的运算。 椭圆曲线密码学是多种数字签名算法的基础,例如椭圆曲线数字签…...

2025季度云服务器排行榜
在全球云服务器市场,各厂商的排名和地位并非一成不变,而是由其独特的优势、战略布局和市场适应性共同决定的。以下是根据2025年市场趋势,对主要云服务器厂商在排行榜中占据重要位置的原因和优势进行深度分析: 一、全球“三巨头”…...

安宝特案例丨Vuzix AR智能眼镜集成专业软件,助力卢森堡医院药房转型,赢得辉瑞创新奖
在Vuzix M400 AR智能眼镜的助力下,卢森堡罗伯特舒曼医院(the Robert Schuman Hospitals, HRS)凭借在无菌制剂生产流程中引入增强现实技术(AR)创新项目,荣获了2024年6月7日由卢森堡医院药剂师协会࿰…...
C++.OpenGL (20/64)混合(Blending)
混合(Blending) 透明效果核心原理 #mermaid-svg-SWG0UzVfJms7Sm3e {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg-SWG0UzVfJms7Sm3e .error-icon{fill:#552222;}#mermaid-svg-SWG0UzVfJms7Sm3e .error-text{fill…...
【Android】Android 开发 ADB 常用指令
查看当前连接的设备 adb devices 连接设备 adb connect 设备IP 断开已连接的设备 adb disconnect 设备IP 安装应用 adb install 安装包的路径 卸载应用 adb uninstall 应用包名 查看已安装的应用包名 adb shell pm list packages 查看已安装的第三方应用包名 adb shell pm list…...

抽象类和接口(全)
一、抽象类 1.概念:如果⼀个类中没有包含⾜够的信息来描绘⼀个具体的对象,这样的类就是抽象类。 像是没有实际⼯作的⽅法,我们可以把它设计成⼀个抽象⽅法,包含抽象⽅法的类我们称为抽象类。 2.语法 在Java中,⼀个类如果被 abs…...