leetcode14最长公共前缀多解法

题目链接

解法一:按列比较,选第一个字符为比较对象,若长度达到所有字符串中最短的字符长度,或者有不符合的出现,返回结果。时间击败了7.28%的人。

class Solution {
        public String longestCommonPrefix(String[] strs) {
            String s = "";
            if (strs.length < 1)
                return "";
            for (int i = 0; i < strs[0].length(); i++) {
                char c = strs[0].charAt(i);
                for (int j = 1; j < strs.length; j++) {
                    if (strs[j].length() <= i || strs[j].charAt(i) != c)
                        return s;
                }
                s += c;
            }
            return s;
        }
    }

解法二:分治算法,将字符串数组分两半来算,然后再比较两个两半得到的结果,击败了99%。

 class Solution {
        public String longestCommonPrefix(String[] strs) {
            int len = strs.length;
            if (len < 1)
                return "";
            return dfs(strs, 0, len - 1);
        }

        private String dfs(String[] strs, int begin, int end) {
            if (end <= begin) {
                return strs[begin];
            }
            int mid = (begin + end) >> 1;
            String a = dfs(strs, begin, mid);
            String b = dfs(strs, mid + 1, end);

            int length = Math.min(a.length(), b.length());
            int index = 0;
            while (index < length && a.charAt(index) == b.charAt(index)) {
                index++;
            }
            return a.substring(0, index);
        }
    }

解法三:在评论区找到的一个巧妙解法,排序字符串数组,再比较第一个和最后一个即可,击败87%。

 class Solution {
        public String longestCommonPrefix(String[] strs) {
            if (strs.length < 1)
                return "";
            Arrays.sort(strs);
            int index = 0;
            int min = Math.min(strs[0].length(), strs[strs.length - 1].length());
            for (int i = 0; i < min; i++) {
                if (strs[0].charAt(i) != strs[strs.length - 1].charAt(i))
                    break;
                index++;
            }
            return strs[0].substring(0, index);
        }
    }

解法四:使用字典树(trim)算法,这个模板还是很有用的,需要根据题目需求在最基础的模板做一些修改,在细节处debug找了很久,最后击败了85%。

 class Solution {
        trie root;

        class trie {
            int flag;
            trie[] cnt;

            public trie() {
                this.flag = 0;
                cnt = new trie[26];
                for (int i = 0; i < 26; i++)
                    cnt[i] = null;
            }

            public void insert(String s) {
                trie tmp = root;
                for (int i = 0; i < s.length(); i++) {
                    int num = s.charAt(i) - 'a';
                    if (tmp.cnt[num] == null) {
                        tmp.cnt[num] = new trie();
                    }
                    tmp = tmp.cnt[num];
                    tmp.flag++;
                }
            }

            public int find(String s, int n) {
                trie tmp = root;
                for (int i = 0; i < s.length(); i++) {
                    int num = s.charAt(i) - 'a';
                    if (tmp.cnt[num].flag < n || tmp.cnt[num] == null)
                        return i;
                    tmp = tmp.cnt[num];
                }
                return s.length();
            }
        }

        public String longestCommonPrefix(String[] strs) {
            //trie树
            if (strs.length < 1 || strs == null)
                return "";
            root = new trie();
            for (int i = 0; i < strs.length; i++) {
                root.insert(strs[i]);
            }
            root.flag = strs.length;
            int len = root.find(strs[0], strs.length);
            return strs[0].substring(0, len);
        }
    }

虽然是一道简单题目,前面两种算法很快就想出了,但是后面复习了分治算法和字典树算法,其中分治很快自己写出来了,字典树是忘记了又去看了一遍自己写的,一下午就过了,还算有点收获。

原文地址:https://www.cnblogs.com/alike/p/13536333.html