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

回文字串---开始刷题1

首先明确“回文”串 是什么:是一个字符串在正读和反读时完全相同。也就是,把这个字符串从中间对折,左右两边的字符能够完全重合。

数学定义:对于一个长度为n的字符串S,如果对于所有的 0<=i<n,都满足s[i] == s[n-1-i],那么该字符串就是回文串。

一些示例:
类型示例说明
单词/字母madam,racecar,level忽略大小写后正反读一致
数字串12321,1221,666数字序列对称
中文上海自来水来自海上汉字序列对称
特殊a,aa,""(空串)单个字符和空串也被视为回文
回文串通常考察:

1、双指针技巧:使用头尾两个指针向中间逼近来判断是否为回文(时间复杂度O(n),空间复杂度O(1))。

2、动态规划:解决“最长回文子串”、“回文子串计数”等问题。

3、字符串哈希/Manacher算法:用于在O(n)时间内高效查找所有回文子串。

4、递归与分治:判断回文本身具有天然的递归结构。

力扣题---解决寻找最长回文子串问题;

第一步:先用人脑模拟一下:(每个子串都有一个中心,可以使用中心扩展法)

对于“babad”:

以b(索引0)为中心向两边扩-》只有b自己,长度1;

以a(索引1)为中心向两边扩-》b-a-b ;长度3;

以b(索引2)为中心向两边扩-》a-b-a;长度3;

以a(索引3)为中心向两边扩-》b-a-d;不是回文串,只有a自己

以d(索引4)为中心向两边扩-》只有d

关键洞察:每个回文串一定有一个“中心”。我们只需要枚举每一个可能的中心,然后向两边扩展,记录最长的即可。

但是需要注意:回文可能是奇数长度(aba,中心是一个字符),也可能是偶数长度(如bb,中心是两个字符之间的缝隙)。所以每个位置要尝试两种中心。

先判断的是否相等,然后再进行的-1 ,两边都进行了-1 ;因此都是多走了一步,需要用right-left-1;得到的就是长度;

使用这种扩展中心法来先写代码:
正确的验证可通过的代码:
func longestPalindrome(s string) string { if len(s)==0{ return "" } start , maxLen := 0,1 //记录最长回文的起始位置和长度 //expandAroundCenter 从给定的左右中心向两边扩展,返回回文长度 expandAroundCenter := func(left,right int)int { for left >= 0 && right < len(s)&&s[left]==s[right] { left-- right++ } //循环结束时 left 和 right 各自走了一步 return right - left -1 } for i := 0 ; i <len(s) ; i++ { // 情况1:奇数长度回文,中心是s[i] oddLen := expandAroundCenter(i,i) //情况2:偶数长度回文,中心是s[i] 和 s[i+1]之间 evenLen := expandAroundCenter(i,i+1) //取两者较大值 curLen := oddLen if evenLen > curLen { curLen = evenLen } // 更新全局最优 if curLen >maxLen{ maxLen = curLen start = i -(maxLen-1)/2 //推导,中心i向左偏移(len-1)/2 } } return s[start:start+maxLen] }

正确运行的结果:

这部分代码是我根据梳理完思路后自己又写了一遍;有一些错误的点,
func lenlongStr (s string )string{ if len(s)==0{ return "" } // 计算回文串长度方案 exelenStr := func (left,right) int { for left >0 && right < len(s) && s[left]==s[right] { left-- rigth++ } ruturn right -left -1 // 两个都有多走一步,因为先进行的相等判断,直接向下各走一步 } start , maxlen := 0,1 // 用来获取最后要输出的串,以及获取最大的长度的回文串 for i := 0 ; i< len(s) ;i++{ //回文串是奇数,中心为i oddlen := exelenStr(i,i) // 回文串是偶数,中心为i 和i+1 explen := exelenStr(i,i+1) //设置一个变量,获取两种中心串的最大值; curlen := oddlen if explen > curlen{ curlen := explen } //再去实际的赋值到 maxlen 这个最大值 上 if curlen > maxlen{ maxlen := curlen start := i - (maxlen-1)/2 //起始值距离 i ,用i这个中心减去长度的一半 } } ruturn s[start,start+maxlen] }

在这里纠正相关的错误点;直接让ai检查的

你这次自己默写的代码非常有价值!虽然报错很多,但核心逻辑(中心扩展法)你已经完全掌握了,这说明你的思路是正确的。

现在的问题纯粹是Go 语言语法细节变量作用域的坑。对于新手来说,这些都是必经之路。我帮你把问题逐一拆解:

🔍 错误清单与修复

1. 函数参数必须声明类型
  • 你的代码func (left,right) int {
  • 问题:Go 是强类型语言,闭包函数的参数也必须写明类型。
  • 修复func(left, right int) int {
2. 边界条件少了一个等号(⚠️ 逻辑 Bug)
  • 你的代码for left > 0 && ...
  • 问题:如果回文串刚好从索引0开始(比如"aba"),left减到0时,left > 0为假,循环提前退出,导致漏掉首字符。
  • 修复:必须是left >= 0
3. 拼写错误三连
  • rigth++→ 应为right++
  • ruturn→ 应为return(出现了两次)
  • lenlongStr→ 题目要求的函数名是longestPalindrome(LeetCode 会因找不到入口函数而报错)
4. 变量作用域陷阱(⚠️ 最隐蔽的 Bug)

这是新手在 Go 中最容易踩的坑:

// ❌ 你的代码 if explen > curlen { curlen := explen // 这里用 := 创建了一个新的局部变量! } // 出了 if 块,这个新 curlen 就消失了 // 外面的 curlen 依然是 oddlen! if curlen > maxlen { maxlen := curlen // 同样的问题!创建了新的局部 maxlen start := i - (maxlen-1)/2 // 创建了新的局部 start } // 外层的 start 和 maxlen 从未被更新!
  • 规则:=短变量声明,会在当前块级作用域创建新变量。如果你只是想赋值给外层已有的变量,必须用=
  • 修复
if explen > curlen { curlen = explen // ✅ 用 = 赋值 } if curlen > maxlen { maxlen = curlen // ✅ 用 = 赋值 start = i - (maxlen-1)/2 // ✅ 用 = 赋值 }

✅ 修正后的完整代码

func longestPalindrome(s string) string { if len(s) == 0 { return "" } // 1. 参数加类型;2. left >= 0;3. right 拼写正确 exelenStr := func(left, right int) int { for left >= 0 && right < len(s) && s[left] == s[right] { left-- right++ } return right - left - 1 // ruturn → return } start, maxlen := 0, 1 for i := 0; i < len(s); i++ { oddlen := exelenStr(i, i) explen := exelenStr(i, i+1) curlen := oddlen if explen > curlen { curlen = explen // ✅ := 改为 = } if curlen > maxlen { maxlen = curlen // ✅ := 改为 = start = i - (maxlen-1)/2 // ✅ := 改为 = } } return s[start : start+maxlen] // ruturn → return,切片语法用冒号 }

💡 给你的学习建议

  1. 关于:=vs=:这是 Go 新手第一道坎。记住口诀:第一次出现用:=,后续修改用=。在if/for块内修改外层变量时,永远只用=
  2. 不要气馁:你第一次独立默写就能把中心扩展法的框架、奇偶双中心、长度计算公式全部写对,这比很多刷了几十题的人还强。剩下的只是语法熟练度问题。
  3. 下一步练习:把修正后的代码再删掉,凭记忆重写一遍。这次重点关注>==和拼写。当你能一次性无错写出来时,这道题就真正属于你了。

你已经走在正确的路上了,继续加油!💪

加油加油!今天就先到这里了!

http://www.jsqmd.com/news/1151547/

相关文章:

  • 西安零担货运系统开发公司排名,运费阶梯计价代码实现
  • 【大数据毕业设计】基于网络数据采集的宁波五金电商营销趋势可视化系统的设计与实现 基于 Django 的宁波五金店铺线上营销流量分析系统(源码+文档+远程调试,全bao定制等)
  • Pygame Sprite 移动封装实战:Vector2 归一化解决斜向速度 1.4 倍问题
  • 前端day5
  • Python 多线程数据同步方案
  • 模板方法模式
  • 昆仑万维四大AI模型技术解析与本地部署实践指南
  • 损失函数(loss)
  • 机器学习评估指标避坑指南:当类别不平衡时,为何 95% 准确率不如 0.3 Kappa?
  • Phylomatic-awk + R 本地化部署:3步构建植物系统发育树避坑指南
  • 必须知道!这家推拉力测试机厂家凭什么好评如潮?
  • CTF Crypto 凯撒密码解题WriteUp
  • MonkeyCode:重新定义AI编程的云原生IDE架构
  • 昆仑万维四大AI模型解析:从世界模型到视频生成的应用指南
  • Grok-1 314B MoE 模型部署实战:8xA100 服务器配置与 300GB 权重下载指南
  • 网络爬虫反爬对抗策略
  • 长期 Agent 的记忆问题:过去什么时候还有资格影响现在
  • ONNX opset 18 算子兼容性实战:PyTorch 2.3 模型转换的 3 个常见错误与修复
  • 解锁科学计算神器:MATLAB 功能全解析与新手入门指南
  • 西安物流货运小程序哪家靠谱,货主司机双向评价模块开发
  • ABM 与大数据挖掘融合:3种数据驱动智能体行为规则设计方法对比
  • 面试官:“现在都是Vibe Coding,你说说你的优势是什么?”,我笑了:“没经验的人,让AI写的代码就是一坨。。”,面试官:“细聊经验”
  • 职称论文写作太难了?2026年用AI辅助写职称论文的完整攻略
  • Pygame 2.5.5 飞机大战实战:面向对象设计 8 个核心类与 4 大模块
  • 实时交通预测失效?Gemini重构Google Maps分析链路,98.2%准确率背后的7层推理架构
  • HarmonyOS鸿蒙PC三方库移植:使用 lycium框架移植libzen (ZenLib)踩坑笔记
  • 大数据计算机毕设之基于 Django 大数据的电商用户偏好画像研判系统的设计与实现 基于数据建模的电商用户画像智能分析系统(完整前后端代码+说明文档+LW,调试定制等)
  • 终极指南:如何用umy-ui轻松解决Vue大数据表格卡顿问题
  • 混元3d生成3d模型 blender使用Quad Remesher Bridge 1.3.2重拓扑 mixmo 或者autoRigPro骨骼绑定
  • 滴滴二面:你的RAG项目太老了,很多技术都不是主流的。我说:最新的我也在跟,而且我学的很快。他说:大模型时代,学的慢就不用学了