hihocoder 1261 String Problem II (Trie樹)
時間限制:50000ms
單點時限:5000ms
記憶體限制:512MB
描述
我們有一個字串集合S,其中有N個兩兩不同的字串。還有M個詢問,每個詢問都會先給出一個字串w,你需要回答以下三個問題:
1. 輸出所有S的串中,可以由w恰好新增兩個字元得到的串中,編號最小的3個。
2. 輸出所有S的串中,可以由w修改不超過2個字元得到的串中,編號最小的3個。
3. 輸出所有S的串中,可以由w刪除恰好兩個字元得到的串中,編號最小的3個。
字母可以新增在包括開頭結尾在內的任意位置,比如在"abc"中新增"x"和"y",可能可以得到"yxabc","aybxc","axbyc"等等的串。
所有字串只由小寫字母構成。
輸入
第一行兩個數N和M,表示集合S中字串的數量和詢問的數量。
接下來N行,其中第i行給出S中第i個字串。第i個字串的編號就是i。
接下來M行,其中第i行給出第i個詢問串。
資料範圍:
N,M<=10000。
S中字串長度和<=100000。
所有詢問中字串長度和<=100000。
輸出
對每個詢問輸出三行,每行三個數,分別表示每個問題編號最小的3個串的編號,從小到大排列。
如果不到3個串,則在最後用-1補到3個輸出,比如如果結果是1和2,那麼輸出1 2 -1,如果S中沒有滿足條件的串,就輸出-1 -1 -1。
5 5 dsxmlkxp asxglqkdxp asxgavxp asxglp sxglkx kebvpyky hjpntqft asxglkxp polbmzgq jdczlmtd樣例輸出
-1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 2 -1 -1 1 3 -1 4 5 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
題目連結:http://hihocoder.com/problemset/problem/1261
題目分析:是1260的擴充,正解應該是字串hash,Trie的複雜度理論會T,資料水了,Trie的思想和1260類似,就是在刪除和修改的地方轉移不同罷了,注意有個剪枝就是修改的時候如果列舉值和當前一樣則跳過
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <set>
using namespace std;
int const MAX = 1e5 + 5;
int n, m, len;
char s[MAX];
struct Trie
{
int next[MAX * 26][26], id[MAX * 26], tot, root, num, cou, res[5];
set <int> ans;
set <int> :: iterator it;
inline int Newnode()
{
memset(next[tot], -1, sizeof(next[tot]));
return tot ++;
}
inline void Init()
{
tot = 0;
root = Newnode();
}
inline void Clr()
{
cou = 0;
ans.clear();
}
inline void Insert(char *s, int no)
{
int p = root;
for(int i = 0; i < (int) strlen(s); i++)
{
int idx = s[i] - 'a';
if(next[p][idx] == -1)
next[p][idx] = Newnode();
p = next[p][idx];
}
id[p] = no;
}
inline void DFS1(char *s, int pos, int p, int cnt)
{
if(id[p] && cnt == 0 && pos == len)
{
ans.insert(id[p]);
return;
}
if(cnt > 0)
for(int i = 0; i < 26; i++)
if(next[p][i] != -1)
DFS1(s, pos, next[p][i], cnt - 1);
if(pos == len)
return;
int idx = s[pos] - 'a';
if(next[p][idx] != -1)
DFS1(s, pos + 1, next[p][idx], cnt);
}
inline void DFS2(char *s, int pos, int p, int cnt)
{
if(id[p] && pos == len)
{
ans.insert(id[p]);
return;
}
int idx = s[pos] - 'a';
if(cnt > 0 && pos <= len)
for(int i = 0; i < 26; i++)
if(next[p][i] != -1 && i != idx)
DFS2(s, pos + 1, next[p][i], cnt - 1);
if(pos == len)
return;
if(next[p][idx] != -1)
DFS2(s, pos + 1, next[p][idx], cnt);
}
inline void DFS3(char *s, int pos, int p, int cnt)
{
if(id[p] && pos == len && cnt == 0)
{
ans.insert(id[p]);
return;
}
if(cnt > 0)
DFS3(s, pos + 1, p, cnt - 1);
if(pos == len)
return;
int idx = s[pos] - 'a';
if(next[p][idx] != -1)
DFS3(s, pos + 1, next[p][idx], cnt);
}
inline void Output()
{
for(it = ans.begin(); it != ans.end() && cou != 3; it++)
res[cou ++] = *it;
for(int i = cou; i < 3; i++)
res[i] = -1;
printf("%d %d %d\n", res[0], res[1], res[2]);
}
}t;
int main()
{
t.Init();
scanf("%d %d", &n, &m);
for(int i = 0; i < n; i++)
{
scanf("%s", s);
t.Insert(s, i + 1);
}
for(int i = 0; i < m; i++)
{
scanf("%s", s);
len = strlen(s);
t.Clr();
t.DFS1(s, 0, t.root, 2);
t.Output();
t.Clr();
t.DFS2(s, 0, t.root, 2);
t.Output();
t.Clr();
t.DFS3(s, 0, t.root, 2);
t.Output();
}
}
相關文章
- hihocoder 1260 String Problem I (Trie樹 好題)
- hihocoder trie 樹
- hihocoder 1014 Trie樹 (Trie 記模板 陣列+指標)陣列指標
- Trie樹,字典樹
- 【Tire 求字典出現的字首個數】hihocoder 1014 Trie樹
- 字典樹(Trie)
- 山科 STUST OJ Problem B: 編寫函式:String to Double (II) (Append Code)函式APP
- 雙陣列TRIE樹Double-Array Trie理解引導陣列
- 線段樹也能是 Trie 樹 題解
- 由簡入繁--Trie樹實戰
- Trie樹:字串頻率統計排序字串排序
- 【動畫】看動畫輕鬆理解「Trie樹」動畫
- 雙陣列字典樹(Double Array Trie)陣列
- 字串演算法--$\mathcal{KMP,Trie}$樹字串演算法KMP
- [翻譯]資料結構——trie樹介紹資料結構
- 【Ac自動機 查詢是否存在一個字典中的字串】hihocoder 1036 Trie圖字串
- LeetCode-Reverse Words in a String IILeetCode
- 208. 實現 Trie (字首樹)-pythonPython
- Codeforces 954I Yet Another String Matching Problem
- hihocoder 1192 簡單的樹嵌入 (樹上DFS 構造 好題)
- 淺談樹形結構的特性和應用(上):多叉樹,紅黑樹,堆,Trie樹,B樹,B+樹...
- 雙陣列Trie樹高效構建有向無環圖陣列
- LeetCode 1032. Stream of Characters 4行Trie樹LeetCode
- Java雙陣列Trie樹的實現方案總結Java陣列
- hihocoder1224 賽車(樹的深度相關)
- Trie
- AC自動機+trie樹實現高效多模式匹配字典模式
- hihocoder 1078 線段樹的區間修改 (線段樹 區間更新 模板)
- hihoCoder 1107 Shortest Proper Prefix (字典樹的遍歷)
- hduoj1002 A + B Problem II (大數相加 字串模擬)字串
- POJ 3468 A Simple Problem with Integers(線段樹區間操作)
- POJ 3468 A Simple Problem with Integers (線段樹 區間更新)
- Trie樹【P3879】 [TJOI2010]閱讀理解
- 一個簡單的統計問題(解決方案:Trie樹)
- 基於PHP + TRIE樹實現敏感詞過濾演算法PHP演算法
- 怎樣實現基於Trie樹和字典的分詞功能分詞
- POJ 3468 A Simple Problem with Integers (線段樹 區間共加)
- POJ 3468-A Simple Problem with Integers(區間更新線段樹)