14. 最长公共前缀
Posted boboboo610
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了14. 最长公共前缀相关的知识,希望对你有一定的参考价值。
编写一个函数来查找字符串数组中的最长公共前缀。
如果不存在公共前缀,返回空字符串 ""。
示例 1:
输入: ["flower","flow","flight"]
输出: "fl"
示例 2:
输入: ["dog","racecar","car"]
输出: ""
解释: 输入不存在公共前缀。
说明:
所有输入只包含小写字母 a-z 。
来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/longest-common-prefix
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。
法一:
1 public String longestCommonPrefix(String[] strs) { 2 if (strs.length == 0) 3 return ""; 4 String ans = strs[0]; 5 //指针i指向字符串数组strs[i],指针j指向公共子串ans 6 for (int i = 1; i < strs.length; i++) { 7 int j = 0; 8 //将公共子串依次与每一个字符串比较 9 while (j < strs[i].length() && j < ans.length()) { 10 if (ans.charAt(j) != strs[i].charAt(j)) 11 break; 12 j++; 13 } 14 ans = ans.substring(0, j); 15 //一旦出现空串,则后面再无需比较 16 if (ans.equals("")) 17 return ""; 18 } 19 return ans; 20 }
法二:
1 public String longestCommonPrefix(String[] strs) { 2 if (strs.length == 0) 3 return ""; 4 String s = strs[0]; 5 for (int i = 1; i < strs.length; i++) { 6 while (strs[i].indexOf(s) != 0){ 7 s = s.substring(0,s.length()-1); 8 if(s.isEmpty()) 9 return ""; 10 } 11 } 12 return s; 13 }
每次查找前串在后串起始位置(indexof方法),只要不为零,截去前串最后一位,继续比较,直到要不前串为空串退出返回,要不前串一直截取直到为后串前缀,然后此作为公共前缀与下一位字符串比较。
法三:
1 public String longestCommonPrefix(String[] strs) { 2 if (strs.length == 0) 3 return ""; 4 String s = strs[0]; 5 for (int i = 0; i < s.length(); i++) { 6 char c = s.charAt(i); 7 for (int j = 1; j < strs.length; j++) { 8 if(i == strs[j].length() || strs[j].charAt(i) != c) 9 return s.substring(0,i); 10 } 11 } 12 return s; 13 }
以str[0]为基准,依次与剩下字符串比较各个位char
1.当基准串与所有比较串比完,且基准串遍历完,则基准串为最长前缀
2.当其中之一比较串比完,则该比较串为最长前缀
3.当基准串与比较串有一个char不同时,相同部分为最长前缀
法三:
1 public String longestCommonPrefix(String[] strs) { 2 if (strs.length == 0) 3 return ""; 4 return feng(strs,0,strs.length-1); 5 6 } 7 8 private String feng(String[] ss, int l, int r){ 9 if(l == r) 10 return ss[l]; 11 12 int mid = (l + r)/2; 13 String s1 = feng(ss, l, mid); 14 String s2 = feng(ss,mid+1,r); 15 16 return zhi(s1,s2); 17 } 18 19 private String zhi(String s1,String s2){ 20 int len = Math.min(s1.length(),s2.length()); 21 for (int i = 0; i < len; i++) { 22 if(s1.charAt(i) != s2.charAt(i)) 23 return s1.substring(0,i); 24 } 25 return s1.substring(0,len); 26 }
分治算法,分到两个字符比较相同前缀,治截取两个字符串相同前缀
法五:
1 public static String longestCommonPrefix(String[] strs) { 2 if (strs.length == 0) 3 return ""; 4 int len = Integer.MAX_VALUE; 5 //找到最短字符串长度 6 for (String s : strs) { 7 len = Math.min(s.length(), len); 8 } 9 int l = 0, r = len, mid = 0; 10 while (l <= r) { 11 mid = (l + r) / 2; 12 //如果全是以s开头,则前一半为公共前缀,再更新 l = mid +1,查找后一半的前一半是否为公共前缀 13 //如果有不是s开头的,则更新r = mid -1,查找前一半的前一半是否为公共前缀 14 //直至L>R,退出二分查找 15 if(fen(strs,mid)) 16 l = mid +1; 17 else 18 r = mid -1; 19 } 20 return strs[0].substring(0,(l + r) / 2); 21 22 } 23 24 private static boolean fen(String[] ss,int len){ 25 String s = ss[0].substring(0,len); 26 for (int i = 1; i < ss.length; i++) { 27 if(!ss[i].startsWith(s)) 28 return false; 29 } 30 return true; 31 }
二分查找 找到字符串数组中最短字符串长度,每次二分查找前一半区域是否是所有字符串前缀,如果是则后一半继续二分查找,如果不是则前一半二分查找,直到左右边界指针交错,即L>R
以上是关于14. 最长公共前缀的主要内容,如果未能解决你的问题,请参考以下文章
2021-09-15:最长公共前缀。编写一个函数来查找字符串数组中的最长公共前缀,如果不存在公共前缀,返回空字符串 ““。力扣14。