算法通关村第十二关——字符串反转问题解析

前言

字符串反转是关于字符串算法里的重要问题,虽然不是太难,但需要考虑到一些边界问题。本篇文章就对几道字符串反转题目进行分析。

1.反转字符串

力扣344题,编写一个函数,其作用是将输入的字符串反转过来。输入字符串以字符数组 s 的形式给出。不要给另外的数组分配额外的空间,你必须原地修改输入数组、使用 O(1) 的额外空间解决这一问题。

分析:这是最基础的字符串反转问题,我们除了可以用语言内置函数解决(面试时基本不会让用),还可以采用双指针的办法解决,算法步骤如下:

  1. 设置left = 0, right = strArray.length - 1
  2. left < right时:
    • 交换strArray[left]strArray[right]
    • left右移一位,right左移一位
  3. left >= right时,反转完成,对反转后的字符串数组进行拼接strArray.join(''),最后返回拼接后的字符串

本题代码如下:

/*** @param {character[]} s* @return {void}* */
function reverseStr(s) {// 特判if (s === null || s.length === 0) {return s;}// 双指针交换let left = 0, right = s.length - 1;while (left <= right) {[s[left], s[right]] = [s[right], s[left]];left++;right--;}
}

注意:如果实际给你的是字符串而不是这道题给的字符串数组,就需要利用JS的Array.from(s)将字符串转换为字符串数组

2.每2k个字符就反转前k个字符

力扣541题,给定一个字符串 s 和一个整数 k,从字符串开头算起,每计数至 2k 个字符,就反转这 2k 字符中的前 k 个字符。

  • 如果剩余字符少于 k 个,则将剩余字符全部反转。
  • 如果剩余字符小于 2k 但大于或等于 k 个,则反转前 k 个字符,其余字符保持原样。

分析:这道题没有什么好说的,就是让每2k个字符就反转前k个字符。记得先把字符串转换为字符串数组,如果字符串长度不足k,就反转整个字符串。

代码如下:

// 每2k个字符就反转前k个字符
function reverseStr(s, k) {if (s === null || s.length === 0) {return s;}// 转换为字符串数组const strArray = Array.from(s);const lengthStr = strArray.length;for (let i = 0; i < lengthStr; i += 2*k) {// 字符串长度不足k,就反转整个字符串reverse(strArray, i, Math.min(i + k, lengthStr) - 1);}// 拼接反转后的字符串return strArray.join('');
}/*** 反转字符函数* */
function reverse(strArray, left, right) {while (left < right) {[strArray[left], strArray[right]] = [strArray[right], strArray[left]];left++;right--;}
}

3.仅仅反转字母

力扣917题,给定一个字符串 S,返回 “反转后的” 字符串,其中不是字母的字符都保留在原地,而所有字母的位置发生反转。

分析:首先想到的就是利用双指针和字母对应的ASCII码判断来实现:

  1. 字符串转为字符串数组,left = 0right = Array.length - 1;
  2. left < right
    • 如果两个指针指向的都是字母,就交换位置
    • 如果右指针指向的是字母,左指针不是,则left++
    • 同样如果左指针指向的是字母,右指针不是,则right--
    • 如果两个指针指向的都不是字母,则left++,right--
  3. 拼接反转后的字符串并返回

代码如下:

// 首先想到利用双指针实现
function reverseOnlyLetters(s) {// 特判if (s === null || s.length === 0) {return s;}// 得到字符串数组const strArray = Array.from(s);const lengthStr = s.length;let left = 0, right = lengthStr - 1;while (left < right) {// 两个指针的指向都是字符串if (isLetter(s, left) && isLetter(s, right)) {[strArray[left], strArray[right]] = [strArray[right], strArray[left]];left++;right--;}// 一个指向的是字母,一个不是else if (!isLetter(s, left)) {left++;}else if (!isLetter(s, right)) {right--;}// 两个指针指向的都不是字母else {left++;right--;}}return strArray.join('');
}// 判断当前字符是否是字母
function isLetter(s, index) {if (s.charCodeAt(index) >= 65 && s.charCodeAt(index) <= 90 || s.charCodeAt(index) >= 97 && s.charCodeAt(index) <= 122) {return true;}return false;
}

4.反转字符串里的单词

力扣151题,给你一个字符串 s ,逐个反转字符串中的所有 单词 。单词是由非空格字符组成的字符串。s 中使用至少一个空格将字符串中的 单词 分隔开。请你返回一个反转 s 中单词顺序并用单个空格相连的字符串。
说明:

  • 输入字符串 s 可以在前面、后面或者单词间包含多余的空格。
  • 反转后单词间应当仅用一个空格分隔。
  • 反转后的字符串中不应包含额外的空格。

分析:本题同样可以用语言内置函数来实现,且比较简单,实际应用当中可以,但为了我们加深我们对数据结构的认知,最好还是自己实现一遍。思路大概都是一致的:

  1. 将字符串转换为字符串数组,去除字符串里多余的空格
  2. 反转整个字符串,此时单词字母也是逆序
  3. 再反转每个单词

在这里插入图片描述

本题代码如下:

// 使用内置函数
function reverseWords(s) {// 去除开头和结尾的空格s = s.trim();// 按空格分割字符串,匹配所有空格const reg = /\s+/; const words = s.split(reg);words.reverse();return words.join(' ');
}/*---------------------------------------*/// 不使用内置函数,自己实现
function reverseWords(s) {// 字符串转数组const strArray = Array.from(s);// 得到去除了多余空格后的字符串数组const trimedStrArray =  trimSpaces(strArray);// 得到反转字符串数组reverse(trimedStrArray, 0, trimedStrArray.length - 1 );// 对反转字符串数组的每个单词进行反转const res = reverseEachWord(trimedStrArray);return res.join('');
}/*** 去除字符串数组多余空格* */
function trimSpaces(strArray) {let left = 0, right = 0, arrLength = strArray.length;while (left < arrLength) {// 移除开始位置和重复的空格if (strArray[left] === ' ' && (left === 0 || strArray[left - 1] === ' ')) {left++;} else {strArray[right++] = strArray[left++];}}// 移除末尾空格strArray.length = (strArray[right - 1] === ' ' ? right - 1 : right);return strArray;
}/*** 反转每个单词* */
// 双指针
function reverseEachWord(strArray) {const lengthOfStrArray = strArray.length;let start = 0, end = 0;while (start < lengthOfStrArray) {// 找到一个单词的末尾while (end < lengthOfStrArray && strArray[end] !== ' ') {end++;}// 反转单词,更新start的位置reverse(strArray, start, end - 1);start = end + 1;end++;}return strArray;
}/*** 反转字符串数组* */
function reverse(strArray, start, end) {let left = start, right = end;while (left < right) {[strArray[left], strArray[right]] = [strArray[right], strArray[left]];left++;right--;}
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/65084.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

亚马逊云科技生成式AI技术辅助教学领域,近实时智能应答2D数字人搭建

早在大语言模型如GPT-3.5等的兴起和被日渐广泛的采用之前&#xff0c;教育行业已经在AI辅助教学领域有过各种各样的尝试。在教育行业&#xff0c;人工智能技术的采用帮助教育行业更好地实现教学目标&#xff0c;提高教学质量、学习效率、学习体验、学习成果。例如&#xff0c;人…

应用案例 | 基于三维机器视觉的机器人麻袋拆垛应用解决方案

​Part.1 项目背景 在现代物流和制造行业中&#xff0c;麻袋的拆垛操作是一个重要且频繁的任务。传统的麻袋拆垛工作通常由人工完成&#xff0c;分拣效率较低&#xff0c;人力成本较高&#xff0c;现场麻袋堆叠、变形严重&#xff0c;垛型不规则、不固定&#xff0c;严重影响分…

(2023|PAMI,diffusion 综述)视觉扩散模型

Diffusion models in vision: A survey 公众号&#xff1a;EDPJ&#xff08;添加 VX&#xff1a;CV_EDPJ 进交流群&#xff09; 目录 0. 摘要 1. 简介 2. 通用框架 2.1 去噪扩散概率模型&#xff08;DDPMs&#xff09; 2.2 噪声条件评分网络&#xff08;NCSNs&#xff0…

b站手机缓存文件转MP4

b站缓存的文件 音频、视频、弹幕是分开的 这里我只用到了音频和视频所以只介绍这一部分 b站的缓存视频文件和路径结构如下 默认缓存路径 内部存储\Android\data\tv.danmaku.bilil\download\89720189 文件夹结构 文件夹 c_738583 这是单个视频的缓存文件夹 进入c_738583文件夹…

10. selenium API (二)

目录 1. 多层框架/窗口定位 2. 下拉框处理 2.1 前端界面 2.2 代码 3. 针对 alert 弹窗进行操作 3.1 前端界面 3.2 代码 4. 文件提交 4.1 前端界面 4.2 代码 5. 显示等待 6. 操作浏览器滚动条 7. 截图 8. 浏览器关闭 9. 窗口切换 在上篇文章中&#xff0c;我们学…

day27 String类 正则表达式

String类的getBytes方法 String s "腻害"; byte[] bytes s.getBytes(StandardCharsets.UTF_8); String类的new String方法 String ss "ss我的"; byte[] gbks ss.getBytes("gbk"); String gbk new String(gbks, "gbk"); String类的…

交换机端口安全实验

文章目录 一、实验的背景与目的二、实验拓扑三、实验需求四、实验解法1. PC配置IP地址部分2. 在SW1上开启802.1X身份验证3. 创建一个用户身份验证的用户。用户名为wangdaye&#xff0c;密码为1234564.创建一个端口隔离组&#xff0c;实现三台PC无法互相访问 摘要&#xff1a; 本…

Kubernetes技术--使用kubeadm快速部署一个K8s集群

这里我们配置一个单master集群。(一个Master节点,多个Node节点) 1.硬件环境准备 一台或多台机器,操作系统 CentOS7.x-86_x64。这里我们使用安装了CentOS7的三台虚拟机 硬件配置:2GB或更多RAM,2个CPU或更多CPU,硬盘30GB或更多 2.主机名称和IP地址规划 3. 初始化准备工作…

【C++技能树】继承概念与解析

Halo&#xff0c;这里是Ppeua。平时主要更新C&#xff0c;数据结构算法&#xff0c;Linux与ROS…感兴趣就关注我bua&#xff01; 继承 0. 继承概念0.1 继承访问限定符 1. 基类和派生类对象赋值兼容转换2. 继承中的作用域3. 派生类中的默认成员函数4.友元5.继承中的静态成员6.菱…

创建性-构造者设计模式

前言 我们在使用Retrofit等这些第三方框架的时候&#xff0c;发现他们的使用都很方便&#xff0c;比如Retrofit retrofit new Retrofit.Builder().build()&#xff0c;和我们通常直接new一个对象不同&#xff0c;他是交给Builder类&#xff0c;通过build()函数来构造一个Retro…

2023-9-2 染色法判定二分图

题目链接&#xff1a;染色法判定二分图 #include <iostream> #include <cstring> #include <algorithm>using namespace std;const int N 100010l, M 200010;int n, m; int h[N], e[M], ne[M], idx;int color[N];void add(int a, int b) {e[idx] b, ne[id…

【Flutter】Flutter 使用 percent_indicator 实现基于百分比显示进度

【Flutter】Flutter 使用 percent_indicator 实现基于百分比显示进度 文章目录 一、前言二、安装和基本使用三、圆形百分比指示器四、线性百分比指示器五、完整示例六、总结 一、前言 今天我要为你介绍一个非常实用的Flutter包——percent_indicator。这个包允许我们基于百分比…

视频融合平台EasyCVR视频汇聚平台关于小区高空坠物安全实施应用方案设计

近年来&#xff0c;随着我国城市化建设的推进&#xff0c;高楼大厦越来越多&#xff0c;高空坠物导致的伤害也屡见不鲜&#xff0c;严重的影响到人们的生命安全。像在日常生活中一些不起眼的小东西如烟头、鸡蛋、果核、易拉罐&#xff0c;看似伤害不大&#xff0c;但只要降落的…

​7.3 项目3 贪吃蛇(控制台版) (A)​

C自学精简实践教程 目录(必读) 主要考察 模块划分 / 文本文件读取 UI与业务分离 / 模块划分 控制台交互 / 数据抽象 需求 用户输入字母表示方向&#xff0c;实现贪吃蛇游戏 规则&#xff1a;碰到边缘和碰到蛇自己都算游戏结束 输入文件 data.txt data.txt 内容如下&am…

深入探讨梯度下降:优化机器学习的关键步骤(二)

文章目录 &#x1f340;引言&#x1f340;eta参数的调节&#x1f340;sklearn中的梯度下降 &#x1f340;引言 承接上篇&#xff0c;这篇主要有两个重点&#xff0c;一个是eta参数的调解&#xff1b;一个是在sklearn中实现梯度下降 在梯度下降算法中&#xff0c;学习率&#xf…

设计模式—职责链模式(Chain of Responsibility)

目录 思维导图 什么是职责链模式&#xff1f; 有什么优点呢&#xff1f; 有什么缺点呢&#xff1f; 什么场景使用呢&#xff1f; 代码展示 ①、职责链模式 ②、加薪代码重构 思维导图 什么是职责链模式&#xff1f; 使多个对象都有机会处理请求&#xff0c;从而避免请…

应急三维电子沙盘数字孪生系统

一、简介应急三维电子沙盘数字孪生系统是一种基于虚拟现实技术和数字孪生技术的应急管理工具。它通过将真实世界的地理环境与虚拟世界的模拟环境相结合&#xff0c;实现了对应急场景的模拟、分析和决策支持。该系统主要由三维电子沙盘和数字孪生模型两部分组成。三维电子沙盘是…

Linux 学习笔记(1)——系统基本配置与开关机命令

目录 0、起步 0-1&#xff09;命令使用指引 0-2&#xff09;查看历史的命令记录 0-3&#xff09;清空窗口内容 0-4&#xff09;获取本机的内网 IP 地址 0-5&#xff09;获取本机的公网ip地址 0-6&#xff09;在window的命令行窗口中远程连接linux 0-7&#xff09;修改系…

Linux串口驱动

《I.MX6ULL 参考手册》第 3561 页的“Chapter 55 Universal Asynchronous Receiver/Transmitter(UART) I.MX6ULL串口原理 1.1UART与USART UART是异步通信&#xff0c;USART是异步/同步通信&#xff0c;比UART多了一条时钟线 USART 的全称是 Universal Synchronous/Asynchr…

抖音视频删了怎么在电脑上找回来

【昨天整理电脑文件时&#xff0c;不小心将剪辑好的抖音作品误删了&#xff0c;但是回收站中找不回来了&#xff0c;这些视频是我花了很多心血制作的&#xff0c;如果没了真的十分可惜&#xff01;希望大家能帮帮我&#xff0c;告诉我应该如何恢复这些文件。】 现在人们都喜欢…