| 12
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
 100
 101
 102
 103
 104
 105
 106
 107
 
 | #include <bits/stdc++.h>using namespace std;
 #define FO(x) freopen(#x".in","r",stdin),freopen(#x".out","w",stdout)
 #define fo(i,j,k) for(int i=(j),end_i=(k);i<=end_i;i++)
 #define fd(i,j,k) for(int i=(j),end_i=(k);i>=end_i;i--)
 #define DEBUG(x) cout<<#x<<"="<<x<<endl;
 #define all(x) (x).begin(),(x).end()
 #define cle(x) memset(x,0,sizeof(x))
 #define ll long long
 #define ull unsigned ll
 #define db double
 #define lb long db
 #define pb push_back
 #define mp make_pair
 #define fi first
 #define se second
 inline int read()
 {
 int x=0; char ch=getchar(); bool f=0;
 for(;ch<'0'||ch>'9';ch=getchar()) if(ch=='-') f=1;
 for(;ch>='0'&&ch<='9';ch=getchar()) x=(x<<3)+(x<<1)+(ch^48);
 return f?-x:x;
 }
 #define CASET fo(___,1,read())
 const int N=3000010;
 const int S=26;
 const int M=19;
 struct AC_Auto{
 int ne[N][S],fail[N],cnt,val[N],rt[M]; bool bo[N];
 AC_Auto() {cnt=1;}
 inline void dfs(int x,int y)
 {
 bo[x]|=bo[y];
 fo(i,0,S-1)
 {
 if(!ne[y][i]) continue;
 else if(!ne[x][i]) ne[x][i]=ne[y][i];
 else dfs(ne[x][i],ne[y][i]);
 }
 }
 queue<int> q;
 inline void getfail(int x)
 {
 for(;!q.empty();q.pop());
 q.push(x); fail[x]=val[x]=0;
 for(int u,p,v;!q.empty();)
 {
 u=q.front(); q.pop();
 for(int i=0;i<S;i++)
 if(v=ne[u][i])
 {
 q.push(v); p=fail[u];
 for(;p&&!ne[p][i];p=fail[p]);
 fail[v]=p?ne[p][i]:x;
 val[v]=val[fail[v]]+bo[v];
 }
 }
 }
 inline void ins(char *s)
 {
 int n=strlen(s+1),u=++cnt,p=u;
 fo(i,1,n)
 {
 ne[u][s[i]-'a']=++cnt;
 u=ne[u][s[i]-'a'];
 }
 bo[u]=1; u=p;
 fo(i,0,M-1)
 if(!rt[i]){rt[i]=u; getfail(rt[i]); break;}
 else {dfs(u,rt[i]); rt[i]=0;}
 }
 inline ll ask(char *s)
 {
 int n=strlen(s+1),c,u;
 ll ans=0;
 fo(j,0,M-1)
 if(rt[j])
 {
 u=rt[j];
 fo(i,1,n)
 {
 c=s[i]-'a';
 if(ne[u][c]) u=ne[u][c];
 else
 {
 for(;u&&!ne[u][c];u=fail[u]);
 u=u?ne[u][c]:rt[j];
 }
 ans+=val[u];
 }
 }
 return ans;
 }
 }A,B;
 char t[300010]; int opt;
 int main()
 {
 CASET
 {
 opt=read(); scanf("%s",t+1);
 if(opt==1) A.ins(t);
 else if(opt==2) B.ins(t);
 else printf("%lld\n",A.ask(t)-B.ask(t));
 fflush(stdout);
 }
 return 0;
 }
 
 |