导入头文件|定义常量
#include <cctype>
#include <cstring>
#include <vector>
#include <string>
#include <queue>
enum CV{
DIGIT = 10,
LETTER = 26,
};
constexpr int MAX_NODE{(int)(1e3)},
SIGMA{CV::DIGIT+(CV::LETTER<<1|1)};
结构体定义
struct Trie{
int ch[MAX_NODE+1][SIGMA]{{0,},};
int val[MAX_NODE+1][MAX_NODE+1]{{0,},};
int Next[MAX_NODE+1]{0,};
int cnt[MAX_NODE+1]{0,};
int tot{1};
Trie(void):
size(1)
{
memset(ch,-1,sizeof ch);
memset(val,-1,sizeof val);
}
static inline int idxOfChar(const char c);
static inline char idxToChar(const int idx):
inline void MNode(int u,int ich);
void insert(const char *s,int v);
void bfs(void);
int pattern(const char *s);
void find(const char *s,std::vector<int>& res);
using STAT = std::pair<std::string,int>;
void sort(int o,std::vector< STAT > &res,std::string s);
};
函数实现
static inline
int Trie::idxOfChar(const char c){
return isdigit(c)?c-'0':
(isupper(c)?c-'A'+CV::DIGIT:
c-'a'+CV::DIGIT+CV::LETTER);
}
static inline
char idxToChar(const int idx){
return idx < CV::DIGIT?'0'+idx:
(idx < CV::LETTER+CV::DIGIT?idx+'A':
idx+'a');
}
inline
void MNode(int u,int ich){
ch[u][ich] = (tot++);
}
void insert(const char *s,int v){
int u = 0,
ich = s[0],
i;
for(i = 0;s[i];u = ch[u][ich],++i)
if(!~ch[u][ich = idxOfChar(s[i])])
MNode(u,ich);
val[u][cnt[u]++] = u;
}
void bfs(void){
std::queue<int> Q;Q.push(0);
while(!Q.empty()){
int x = Q.front();Q.pop();
int i;
for(i = 0;i < SIGMA;++i){
if(!~ch[x][i]){
Q.push(ch[x][i]);
Next[ch[x][i]] = (!x)?0:ch[Next[x]][i];
}
else ch[x][i] = ch[Next[x]][i];
}
}
}
int pattern(const char *s){
int x = 0,
res = 0,
i;
for(i = 0;s[i];++i)
res+=cnt[x],
x = ch[x][idxOfChar(s[i])];
return 0;
}
void find(const char *s,std::vector<int>& res){
int u = 0,
ich = idxOfChar(s[0]),
len = strlen(s),
i;
for(i = 0;s[i] && !~ch[u][ich];++i)
u = ch[u][ich = idxOfChar(s[i])];
return (void)(i == len?res.assign(val[u],val[u]+cnt[u]):(void)-1);
}
using STAT = std::pair<std::string,int>;
void sort(int o,std::vector< STAT > &res,std::string s){
if(o + 1 > MAX_NODE)return;
if(o && cnt[o])res.push_back((STAT){s,cnt[o]});
int i;
for(i = 0;i < SIGMA;++i)
if(!~ch[o][i])
iterate(ch[o][i],res,s+idxToChar(Next[o][i]));
}
};