腾讯的字符串考题居然如此easy,弄清回文串,你也可以进大厂。

383 阅读6分钟

引言:一道“简单题”,能让你原地崩溃?

走进腾讯的大楼,坐在面试官面前,面试官看着你,淡淡地抛出第一个考题:

“用 JS 把 'hello' 反向输出成 'olleh'。”

你以为是送分题,结果写着写着就懵了。这题看似简单,其实暗藏玄机,考验的不只是你会不会写代码,而是你对 JavaScript 的理解有多深。

今天我们就来聊聊这个“反转字符串”的骚操作,顺便带你搞懂 JS 中的一些知识点。


一、怎么把 "hello" 变成 "olleh"?

✅ 最常见做法:split + reverse + join,三连出击!

let str = "hello";
let reversed = str.split("").reverse().join("");
console.log(reversed); // 输出 olleh

这是一个层层递进的过程,我们一步步拆解:

  1. split("") :把字符串“拆开”,变成一个字母数组。

    • "hello" → ['h', 'e', 'l', 'l', 'o']
  2. reverse() :给这个数组来个翻转,把头变成尾,把尾变成头。

    • ['h', 'e', 'l', 'l', 'o'] → ['o', 'l', 'l', 'e', 'h']
  3. join("") :再把这些字母拼回字符串。

    • ['o', 'l', 'l', 'e', 'h'] → "olleh"

这一套操作下来,一个反向字符串就诞生了。


❗ 为什么不能直接 str.reverse()?

那么问题来了,都能直接翻转,为啥不能直接str.reverse,然后返回它的值呢?这不是减少了工作量吗?

你可能会想:“数组都能 reverse,字符串为啥不行?”
嗯……JS 表示它也很无奈。

因为字符串是“基本类型”,就像数字一样,它们不是对象,也没有自己的方法。你想调用 .reverse()?不好意思,没有这个功能。

但 JS 很贴心地偷偷帮你“包装了一下”,这就是传说中的——


二、包装类:JS 的“临时演员”机制

想象一下,当你写:

"hello".toUpperCase(); // HELLO

你其实是在和一个“假对象”打交道。

JavaScript 背后偷偷干了这些事:

  1. 创建一个临时的 new String("hello") 对象
  2. 在这个对象上调用 .toUpperCase();( tips:toUpperCase()方法是将字符串对象转化为全大写 )
  3. 然后立刻把这个对象销毁。

⚠️ 所以,别想着给字符串加属性:

"abc".name = "test"; 
console.log("abc".name); // undefined —— 对于一个简单数据类型,它接受不了这些属性

三、进阶玩法:判断一个字符串是不是“回文”

什么是回文?就是正着读和倒着读都一样的字符串,比如:

  • "madam"
  • "level"
  • "上海自来水来自海上"
  • "yzx被女朋友说是M"

听起来很高大上?其实原理很简单,还是那几个老朋友:

function isPalindrome(str) {
  const cleaned = str.toLowerCase();
  const reversed = cleaned.split("").reverse().join("");
  return cleaned === reversed;
}

来测几个例子:

console.log(isPalindrome("madam"));       // true
console.log(isPalindrome("hello"));       // false
console.log(isPalindrome("Level"));       // true(忽略大小写)
console.log(isPalindrome("上海自来水来自海上")); // true(中文也能行)
console.log(isPalindrome("yzx被女朋友说是M")); // false(中英文混合也能行)

image.png 是不是有种“原来如此”的感觉?


四、总结:小技巧也能玩出花

方法干啥用的
split("")把字符串拆成一个个字符
reverse()数组专属技能,反转顺序
join("")把字符重新拼成字符串
包装类让字符串假装是个对象

别看这些方法简单,它们在js中可是相当重要的。


五、课后挑战:你能更进一步吗?

试试看这些变体题:

  1. 写一个函数,只保留字母并忽略空格、标点后判断是否是回文。

    isPalindrome("A man, a plan, a canal: Panama") // 应该返回 true
    
  • 首先我们要把标点符号去掉;
  • 接着把所有字母变成小写或大写
  • 最后判断是否回文串

这里就要借用一下replace方法了

replace方法:replace 是 JavaScript 字符串对象的一个方法,用于在字符串中查找匹配的子字符串,并将其替换为指定的新字符串。调用方式为:replace(a,b);其中a为一个字符串或一个表达式,用于指定要查找那=哪些内容,而b是一个字符串或一个函数,用于替换前面a的内容。在 JavaScript 中,正则表达式通常用斜杠 // 包裹。

function isPalindrome(str) {
  const cleaned = str.toLowerCase().replace(/[^a-z]/g, '');
  // ^ :在方括号 [] 内使用时,它表示取反。也就是说,匹配除了方括号内指定字符之外的所有字符。
 // a-z :表示从字母 a 到字母 z 的所有小写字母。
// g :是一个修饰符,代表全局匹配(global)。这意味着正则表达式会在整个字符串中查找所有匹配项,
而不是找到第一个匹配项就停止。
  const reversed = cleaned.split('').reverse().join('');
  return cleaned === reversed;
}

2. 写一个函数,找出最长回文子串。

使用中心扩展法来查找字符串 s 中的最长回文子串。

变量初始化

let start = 0 , maxLength = 0 ;
  • start :用于记录最长回文子串的起始索引,初始值为 0。
  • maxLength :用于记录最长回文子串的长度,初始值为 0。

expandAroundCenter 函数

function expandAroundCenter ( left , right ){
while ( left >= 0 && right < s.length && s[left] === s[right]){
left -- ;
right ++ ;
}// 回退一步才是有效的回文范围
const length = right - left - 1 ;
if ( length > maxLength ) {
maxLength = length ;
start = left + 1 ;
      }
   }
  • 功能 :以 left 和 right 为中心向两边扩展,找出以该中心的最长回文子串,并更新 maxLength 和 start 。
  • 参数 :
    • left :回文中心的左索引。
    • right :回文中心的右索引。
  • 实现细节 :
    1. while 循环:只要 left 不越界(大于等于 0)、 right 不越界(小于字符串长度)且左右字符相等,就继续向两边扩展。
    2. 计算长度:循环结束后,由于最后一次扩展使得 left 和 right 超出了回文范围,所以需要回退一步,即 length = right - left - 1 。
    3. 更新 maxLength 和 start :如果当前回文子串的长度大于 maxLength ,则更新 maxLength 为当前长度,并将 start 更新为当前回文子串的起始索引 left + 1 。

遍历字符串

for (let i = 0 ; i < s . length;i++ ) {
expandAroundCenter ( i , i ) ; // 奇数长度回文
expandAroundCenter ( i , i + 1 ) ; // 偶数长度回文
}
  • 使用 for 循环遍历字符串的每个字符。
  • 对于每个字符 i ,分别调用 expandAroundCenter 函数两次:
    • expandAroundCenter(i, i) :以单个字符 i 为中心,查找奇数长度的回文子串。
    • expandAroundCenter(i, i + 1) :以相邻的两个字符 i 和 i + 1 为中心,查找偶数长度的回文子串。

返回结果

return s . slice ( start , start + maxLength ) ;
  • 使用 slice 方法从字符串 s 中提取从 start 开始,长度为 maxLength 的子串,即最长回文子串。
题目学到了什么
忽略标点判断回文正则表达式、字符串清洗、基础逻辑处理
找最长回文子串算法思维、双指针技巧、字符串操作

六、结语:别被“简单题”骗了!

你以为这只是一个小反转字符串的问题?不,这是 JS 基础功的大阅兵!

从字符串的操作到数组的方法,再到 JS 的底层机制——包装类,这一套流程走下来,你就已经从小白升级成了“基础王者”。

所以啊,别小看这些“初级题”,它们才是通往高手之路的关键一步!