[Leetcode] Implement strStr()

Implement strStr().

Returns a pointer to the first occurrence of needle in haystack, or null if needle is not part of haystack.

KMP算法!

 1 class Solution {
 2 public:
 3     void getNext(vector<int> &next, string &needle) {
 4         int i = 0, j = -1;
 5         next[i] = j;
 6         while (i != needle.length()) {
 7             while (j != -1 && needle[i] != needle[j]) j = next[j];
 8             next[++i] = ++j;
 9         }
10     }
11     int strStr(string haystack, string needle) {
12         if (haystack.empty()) return needle.empty() ? 0 : -1;
13         if (needle.empty()) return 0;
14         vector<int> next(needle.length() + 1);
15         getNext(next, needle);
16         int i = 0, j = 0;
17         while (i != haystack.length()) {
18             while (j != -1 && haystack[i] != needle[j]) j = next[j];
19             ++i; ++j;
20             if (j == needle.length()) return i - j;
21         }
22         return -1;
23     }
24 };

上面的是通常用的KMP算法,但是算法是有一定缺陷的。比如我们的模式串  pattern =“AAAAB”,其中很容易得到next数组为01230。如果目标匹配串为 “AAAACAAAAB” ,大家可以模拟一下,A要回溯多次。就是说我们的next数组优化并不彻底。优化算法:next[i]表示匹配串在i处如果匹配失败下次移到的位置。下面是优化后的的求next数组的代码。虽然两种写求得next值不一样,但是kmp函数的写法是一样的。

 1 class Solution {
 2 public:
 3     void getNext(vector<int> &next, string &needle) {
 4         int i = 0, j = -1;
 5         next[i] = j;
 6         while (i < needle.length() - 1) {
 7             while (j != -1 && needle[i] != needle[j]) j = next[j];
 8             ++i; ++j;
 9             //特殊情况,这里即为优化之处。考虑下AAAAB, 防止4个A形成0123在匹配时多次迭代。
10             if (needle[i] == needle[j]) next[i] = next[j]; 
11             else next[i] = j;
12         }
13     }
14     int strStr(string haystack, string needle) {
15         if (haystack.empty()) return needle.empty() ? 0 : -1;
16         if (needle.empty()) return 0;
17         vector<int> next(needle.length() + 1);
18         getNext(next, needle);
19         int i = 0, j = 0;
20         while (i != haystack.length()) {
21             while (j != -1 && haystack[i] != needle[j]) j = next[j];
22             ++i; ++j;
23             if (j == needle.length()) return i - j;
24         }
25         return -1;
26     }
27 };

下面不是KMP算法,但是代码特别简洁:

 1 class Solution {
 2 public:
 3     int strStr(string haystack, string needle) {
 4         int i, j;
 5         for (i = j = 0; i < haystack.size() && j < needle.size();) {
 6             if (haystack[i] == needle[j]) {
 7                 ++i; ++j;
 8             } else {
 9                 i -= j - 1; j = 0;
10             }
11         }
12         return j != needle.size() ? -1 : i - j;
13     }
14 };

 

 

posted @ 2014-04-12 18:19  Eason Liu  阅读(7037)  评论(7编辑  收藏  举报