zoukankan      html  css  js  c++  java
  • LeetCode-028-实现 strStr()

    实现 strStr()

    题目描述:实现 strStr() 函数。

    给你两个字符串 haystack 和 needle ,请你在 haystack 字符串中找出 needle 字符串出现的第一个位置(下标从 0 开始)。如果不存在,则返回 -1 。

    示例说明请见LeetCode官网。

    来源:力扣(LeetCode)
    链接:https://leetcode-cn.com/problems/implement-strstr/
    著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

    解法一:穷举法
    • 首先,如果needle为空,直接返回0;如果 haystack 为空 或者 haystack 的长度 小于 needle 的长度,直接返回-1;
    • 否则,从 haystack 的第一位开始跟 needle 进行匹配,如果匹配不上,则往后继续遍历haystack,直到遍历完成,就能得到结果。

    说明:该方法效率比较差。

    解法二:KMP算法

    首先,构造一个next数组,先计算出下一次跳转的位置,然后遍历按照next数组的位置将原串和匹配串进行匹配。

    import com.google.common.base.Strings;
    
    public class LeetCode_028 {
        /**
         * 穷举法
         *
         * @param haystack
         * @param needle
         * @return
         */
        public static int strStr(String haystack, String needle) {
            if (needle == null || needle.length() == 0) {
                return 0;
            }
            if (haystack == null || haystack.length() == 0 || haystack.length() < needle.length()) {
                return -1;
            }
            int first = 0;
            while (first < haystack.length()) {
                int matchCount = 0;
                for (int i = 0; i < needle.length() && (i + first) < haystack.length(); i++) {
                    if (needle.charAt(i) == haystack.charAt(i + first)) {
                        matchCount++;
                    } else {
                        break;
                    }
                }
                if (matchCount == needle.length()) {
                    return first;
                } else {
                    first++;
                }
            }
            return -1;
        }
    
        /**
         * KMP算法
         *
         * @param haystack 原串
         * @param needle   匹配串
         * @return
         */
        public static int strStr2(String haystack, String needle) {
            if (Strings.isNullOrEmpty(needle)) {
                return 0;
            }
            // 分别获取原串和匹配串的长度
            int haystackLength = haystack.length(), needleLength = needle.length();
            // 原串和匹配串前面都加一个空格,使其下标从1开始
            haystack = " " + haystack;
            needle = " " + needle;
    
            char[] haystackList = haystack.toCharArray();
            char[] needleList = needle.toCharArray();
    
            // 构建 next 数组,数组长度为匹配串的长度(next 数组是和匹配串相关的)
            int[] next = new int[needleLength + 1];
            // 构造过程 i = 2, j = 0 开始,i 小于等于匹配串长度【构造 i 从 2 开始】
            for (int i = 2, j = 0; i <= needleLength; i++) {
                // 匹配不成功的话,j = next[j]
                while (j > 0 && needleList[i] != needleList[j + 1]) {
                    j = next[j];
                }
                // 匹配成功的话,先让 j++
                if (needleList[i] == needleList[j + 1]) {
                    j++;
                }
                // 更新 next[i],结束本次循环, i++
                next[i] = j;
            }
    
            // 匹配过程,i = 1, j = 0 开始,i 小于等于原串长度【匹配 i 从 1 开始】
            for (int i = 1, j = 0; i <= haystackLength; i++) {
                // 匹配不成功 j = next[j]
                while (j > 0 && haystackList[i] != needleList[j + 1]) {
                    j = next[j];
                }
                // 匹配成功的话,先让 j++,结束本次循环后 i++
                if (haystackList[i] == needleList[j + 1]) {
                    j++;
                }
                // 整一段都匹配成功,直接返回下标
                if (j == needleLength) {
                    return i - needleLength;
                }
            }
    
            return -1;
        }
    
        public static void main(String[] args) {
            System.out.println(strStr("mississippi", "issi"));
    
            System.out.println(strStr2("mississippi", "issi"));
        }
    }
    

    【每日寄语】 在最美的年华,做最喜欢的事情,别辜负了美好时光,借时光之手,暖一处花开,借一方晴空,拥抱梦想。

  • 相关阅读:
    HTTPs与HTTP的区别&HTTPs如何建立连接
    HTTP协议常见状态码和字段
    服务器负载均衡
    ARP协议工作原理
    C++智能指针
    C++类型转换
    Rust 只出现一次的数字 两种解法
    Rust 存在重复元素 两种解法
    Rust 旋转数组
    Rust 动态规划 买卖股票的最佳时机 II
  • 原文地址:https://www.cnblogs.com/kaesar/p/15405893.html
Copyright © 2011-2022 走看看