难度:简单
描述:
编写一个函数来查找字符串数组中的最长公共前缀。
如果不存在公共前缀,返回空字符串 “”。
示例 1:
输入:strs = ["flower","flow","flight"]
输出:"fl"
示例 2:
输入:strs = ["dog","racecar","car"]
输出:""
解释:输入不存在公共前缀。
提示:
求最长公共前缀,所以这里只考虑前缀即可,因此可以首先取第一个字符串进行遍历,然后跟字符串数组里的其他字符串按照顺序依次比对每一个字符,直到遇到不同的字符为止。即纵向扫描法。这里借用Leetcode的图解:
首先根据以上思路,自己实现的解法:
class Solution {
public String longestCommonPrefix(String[] strs) {
//最长公共前缀,考虑前缀即可
int index = 0;
boolean flag = true;
String result = "";
for(int i = 0;i < strs[0].length() && flag;i++){
index++;
char current = strs[0].charAt(i);
for(int j = 0;j< strs.length;j++){
if(i >= strs[j].length() || current != strs[j].charAt(i)){
flag = false;
index--;
break;
}
}
}
return index > 0 ? strs[0].substring(0,index):"";
}
}
参考官方的纵向扫描的解法:
class Solution {
public String longestCommonPrefix(String[] strs) {
if (strs == null || strs.length == 0) {
return "";
}
int length = strs[0].length();
int count = strs.length;
for (int i = 0; i < length; i++) {
char c = strs[0].charAt(i);
for (int j = 1; j < count; j++) {
if (i == strs[j].length() || strs[j].charAt(i) != c) {
return strs[0].substring(0, i);
}
}
}
return strs[0];
}
}
复杂度分析:
参考官方的横向扫描法:对字符串数组中的每一项,进行两两对比,找出最长前缀,与数组的下一项再取最长前缀,依次类推。思路简单,但是复杂度没有提高。官方图解:
class Solution {
public String longestCommonPrefix(String[] strs) {
if (strs == null || strs.length == 0) {
return "";
}
String prefix = strs[0];
int count = strs.length;
for (int i = 1; i < count; i++) {
prefix = longestCommonPrefix(prefix, strs[i]);
if (prefix.length() == 0) {
break;
}
}
return prefix;
}
public String longestCommonPrefix(String str1, String str2) {
int length = Math.min(str1.length(), str2.length());
int index = 0;
while (index < length && str1.charAt(index) == str2.charAt(index)) {
index++;
}
return str1.substring(0, index);
}
}
复杂度分析:
参考官方的分治法,自我感觉其实跟横向扫描差不多,只是实现方式不同,时间复杂度理论上是相同的。下面参考官方图解:
class Solution {
public String longestCommonPrefix(String[] strs) {
if (strs == null || strs.length == 0) {
return "";
} else {
return longestCommonPrefix(strs, 0, strs.length - 1);
}
}
public String longestCommonPrefix(String[] strs, int start, int end) {
if (start == end) {
return strs[start];
} else {
int mid = (end - start) / 2 + start;
String lcpLeft = longestCommonPrefix(strs, start, mid);
String lcpRight = longestCommonPrefix(strs, mid + 1, end);
return commonPrefix(lcpLeft, lcpRight);
}
}
public String commonPrefix(String lcpLeft, String lcpRight) {
int minLength = Math.min(lcpLeft.length(), lcpRight.length());
for (int i = 0; i < minLength; i++) {
if (lcpLeft.charAt(i) != lcpRight.charAt(i)) {
return lcpLeft.substring(0, i);
}
}
return lcpLeft.substring(0, minLength);
}
}
时间复杂度分析:
参考官方的二分查找法,自我感觉其实跟纵向扫描法,只是以二分查找的方式确定位数。
class Solution {
public String longestCommonPrefix(String[] strs) {
if (strs == null || strs.length == 0) {
return "";
}
int minLength = Integer.MAX_VALUE;
for (String str : strs) {
minLength = Math.min(minLength, str.length());
}
int low = 0, high = minLength;
while (low < high) {
int mid = (high - low + 1) / 2 + low;
if (isCommonPrefix(strs, mid)) {
low = mid;
} else {
high = mid - 1;
}
}
return strs[0].substring(0, low);
}
public boolean isCommonPrefix(String[] strs, int length) {
String str0 = strs[0].substring(0, length);
int count = strs.length;
for (int i = 1; i < count; i++) {
String str = strs[i];
for (int j = 0; j < length; j++) {
if (str0.charAt(j) != str.charAt(j)) {
return false;
}
}
}
return true;
}
}
复杂度分析
版权说明 : 本文为转载文章, 版权归原作者所有 版权申明
原文链接 : https://blog.csdn.net/zhang_java_11/article/details/125533269
内容来源于网络,如有侵权,请联系作者删除!