HDU 1711 裸KMP,附KMP模板
阿新 • • 發佈:2019-01-26
//pattern為模板串,從0下標,長度為len。 返回next陣列 template<typename T> void kmp_pre(T pattern[], int len, int next[]) { next[0] = next[1] = 0; for(int i = 1 ; i < len ; i++) { int j = next[i]; while(j && pattern[i] != pattern[j]) j = next[j]; next[i+1] = pattern[i] == pattern[j] ? j+1 : 0; } } //text為匹配串,lenT為其長度。pattern為模板串,lenP為其長度,next為上面得到的next陣列。 //返回一個vector,表示所有匹配成功的在text的下標(從0開始) //還返回一個true/false表示是否有匹配成功的 vector<int>ret; template<typename T> bool find(T text[], int lenT, T pattern[], int lenP, int next[], vector<int> &ret)//下標皆為從0開始 { ret.clear(); int j = 0; //初始化在模式串第一個位置 for (int i = 0; i < lenT; ++ i) { while (j && pattern[j] != text[i]) j = next[j]; if (pattern[j] == text[i]) j++; if (j == lenP) { ret.push_back(i-lenP+1); } } return ret.size(); }
上述為模板
AC code
#include <bits/stdc++.h> #include <ext/pb_ds/priority_queue.hpp> #include <tr1/unordered_map> #include <ctime> using std::tr1::unordered_map; /* #include <iostream> #include <cstring> #include <queue> #include <algorithm> #include <cstdio> #include <map> using namespace std; */ using std::sort; using std::bitset; using std::max; using std::cout; using std::stack; using std::cin; using std::endl; using std::swap; using std::pair; using std::vector; using std::set; using std::map; using std::multiset; using std::queue; using std::greater; using std::string; using std::priority_queue; using std::max_element; using std::min_element; using __gnu_pbds::pairing_heap_tag; __gnu_pbds::priority_queue<int, greater<int>, pairing_heap_tag> heap; #define Hash unordered_map #define pr(x) cout<<#x<<" = "<<x<<" " #define prln(x) cout<<#x<<" = "<<x<<endl #define lson o*2, L, M #define rson o*2+1, M + 1,R //extend[i]:y[i...n-1]與x[0...m-1]的最長公共字首 int a[1000010], pat[10010]; //pattern為模板串,從0下標,長度為len。 返回next陣列 template<typename T> void kmp_pre(T pattern[], int len, int next[]) { next[0] = next[1] = 0; for(int i = 1 ; i < len ; i++) { int j = next[i]; while(j && pattern[i] != pattern[j]) j = next[j]; next[i+1] = pattern[i] == pattern[j] ? j+1 : 0; } } //text為匹配串,lenT為其長度。pattern為模板串,lenP為其長度,next為上面得到的next陣列。 //返回一個vector,表示所有匹配成功的在text的下標(從0開始) //還返回一個true/false表示是否有匹配成功的 vector<int>ret; template<typename T> bool find(T text[], int lenT, T pattern[], int lenP, int next[], vector<int> &ret)//下標皆為從0開始 { ret.clear(); int j = 0; //初始化在模式串第一個位置 for (int i = 0; i < lenT; ++ i) { while (j && pattern[j] != text[i]) j = next[j]; if (pattern[j] == text[i]) j++; if (j == lenP) { ret.push_back(i-lenP+1); } } return ret.size(); } int pattern[10010], text[1000010], nxt[10010]; void init() { int lenP, lenT; scanf("%d%d", &lenT, &lenP); for (int i = 0; i != lenT; ++i) scanf("%d", &text[i]); for (int i = 0; i != lenP; ++ i) scanf("%d", &pattern[i]); kmp_pre(pattern, lenP, nxt); find(text, lenT, pattern, lenP, nxt, ret); if (ret.size()==0) printf("-1\n"); else printf("%d\n", ret[0] + 1); } int main() { int T; scanf("%d", &T); while (T--) { init(); } return 0; }