编写一个函数来查找字符串数组中的最长公共前缀。
如果不存在公共前缀,返回空字符串 “”。
示例 1:
输入: [“flower”,”flow”,”flight”]
输出: “fl”
示例 2:
输入: [“dog”,”racecar”,”car”]
输出: “”
解释: 输入不存在公共前缀。
说明:
所有输入只包含小写字母 a-z 。
来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/longest-common-prefix
思路:
暴力:枚举所有字符串的每一列,比较相同列上的字符是否相等,如果相同继续下一列比较
分治:获取[left,mid]
的LCP1
和[mid+1,right]
的LCP2
。对LCP1
和LCP2
求LCP
。
复杂度分析:
暴力:时间复杂度O(mn) m为字符串平均长度,n为strs数组长度。空间复杂度O(1) 无需额外空间。
分治:时间复杂度O(mn),m为字符串平均长度,n为strs数组长度。时间复杂度的递推式为T(n) = 2*T(n/2)+O(m)
,由主定理可算得T(n) =O(mn)
。空间复杂度:O(mlogn),递归调用层数最大为logn,每层需要m的空间存储返回结果。
//暴力
var longestCommonPrefix = function (strs) {
let n = strs.length;
if (n === 0) return "";
let m = strs[0].length;
for (let i = 0; i < m; i++) {
for (let j = 1; j < n; j++) {
let c = strs[0].charAt(i);
if (i === strs[j].length || strs[j].charAt(i) !== c) {
return strs[0].substring(0, i);
}
}
}
return strs[0];
};
//分治
var longestCommonPrefix = function (strs) {
const myLongestCommonPrefix = (strs, start, end) => {
if (start === end) {
return strs[start];
} else {
let mid = (start + end) >> 1;
let left = myLongestCommonPrefix(strs, start, mid);
let right = myLongestCommonPrefix(strs, mid + 1, end);
return commonPrefix(left, right);
}
};
const commonPrefix = (leftStr, rightStr) => {
let minLength = Math.min(leftStr.length, rightStr.length);
for (let i = 0; i < minLength; i++) {
if (leftStr[i] !== rightStr[i]) {
return leftStr.substr(0, i);
}
}
return leftStr.substr(0, minLength);
};
if (strs === null || strs.length === 0) {
return "";
} else {
return myLongestCommonPrefix(strs, 0, strs.length - 1);
}
};