一起养成写作习惯!这是我参与「掘金日新计划 · 4 月更文挑战」的第5天,点击查看活动详情
题目(Valid Palindrome)
链接:https://leetcode-cn.com/problems/valid-palindrome
解决数:2200
通过率:47%
标签:双指针 字符串
相关公司:facebook microsoft amazon
给定一个字符串,验证它是否是回文串,只考虑字母和数字字符,可以忽略字母的大小写。
说明: 本题中,我们将空字符串定义为有效的回文串。
示例 1:
输入: "A man, a plan, a canal: Panama"
输出: true
解释: "amanaplanacanalpanama" 是回文串
示例 2:
输入: "race a car"
输出: false
解释: "raceacar" 不是回文串
提示:
1 <= s.length <= 2 * 105- 字符串
s由 ASCII 字符组成
思路
第一眼看实例1有点懵了又是逗号又是冒号的 为啥是true 这特么的是回文??
然后再看题目强调了: 只考虑字母和数字字符,可以忽略字母的大小写。
它只要 数字 和 字母 (大小不论) , 所以首先 肯定要处理一下这个字符串
我们可以用正则去掉不是字母和数字的 : \W:匹配非 字母、数字、下划线。等价于 '[^A-Za-z0-9_]'
可以直接用[^A-Za-z0-9], 测试用例没有下划线, 用\W 可以通过, 然后跑去提交了条下划线的测试用例
再转换为小写或大写都可以
"A man, a plan, a canal: Panama" => amanaplanacanalpanama
接下来就简单了, 用双指针就能搞定, 就是首尾字符挨个对比, 一旦有一个不相等的就说明不是回文了
代码
正则双指针
/**
* @param {string} s
* @return {boolean}
*/
var isPalindrome = function(s) {
let str = s.replace(/\W|_/g, '').toLowerCase()
let left = 0
let right = str.length - 1
while(left < right){
if(str[left] !== str[right]) return false
left++
right--
}
return true
};
正则加翻转
var isPalindrome = function(s) {
let str = s.replace(/\W|_/g,'').toLowerCase()
let resv = str.split('').reverse().join('')
return str === resv
};
不用正则
var isPalindrome = function(s) {
s = s.toLowerCase()
let i = 0;
let j = s.length - 1
while(i < j){
while(!check(s[i]) && i < s.length) i++
while(!check(s[j]) && j >= 0) j--
if (s[i] === s[j]) {
i++
j--
} else if (j >= 0 && i < s.length) {
return false
}
}
return true
};
// 判断是否是 a-z 和 0 - 9
function check(c){
return !!c && ((c >= 'a' && c <= 'z') || (c.charCodeAt() >= 48 && c.charCodeAt() <= 57))
}