题目

  点这里看题目。

分析

  首先,我们不需要真的从 AC 自动机中把串删掉。由于我们计算贡献和,我们只需要在 AC 自动机上,把已经删除的串的贡献抹掉就可以了。

  接着考虑询问。这是一个很基础的问题,一般我们会在 AC 自动机上面处理出每个状态的贡献和,并且将询问的字符串在 AC 自动机上面跑一跑,答案就是经过的状态的贡献和的贡献和。

  现在贡献是动态的,我们的贡献和也变成了动态的。不过,由于贡献和本质上就是\(fail\)树上到根的路径的贡献和,因此我们可以对\(fail\)树进行树链剖分,修改就是单点修改,查询就查询到根的贡献和。这样就可以用 BIT 来维护一下区间和。

  另一种更简单的方法是,在一个点上改贡献的时候,有且仅有其子树内的点会被影响,因此我们用 BIT 维护差分,每次修改就是将子树内的贡献 +1 ,查询就直接查询。这样做就少了一个\(\log_2n\)。

  这两种方法体现了两种不同的思想——统计贡献维护贡献;两者需要具体问题具体分析再选择使用。

代码

#include <cstdio>
#include <iostream>
using namespace std; #define Tour( c ) for( int c = 0 ; c < 26 ; c ++ )
#define up( x ) ( x += ( x & ( -x ) ) )
#define down( x ) ( x -= ( x & ( -x ) ) ) typedef long long LL; const int MAXN = 1e5 + 5, MAXL = 1e6 + 5; template<typename _T>
void read( _T &x )
{
x = 0;char s = getchar();int f = 1;
while( s > '9' || s < '0' ){if( s == '-' ) f = -1; s = getchar();}
while( s >= '0' && s <= '9' ){x = ( x << 3 ) + ( x << 1 ) + ( s - '0' ), s = getchar();}
x *= f;
} template<typename _T>
void write( _T x )
{
if( x < 0 ){ putchar( '-' ); x = ( ~ x ) + 1; }
if( 9 < x ){ write( x / 10 ); }
putchar( x % 10 + '0' );
} struct edge
{
int to, nxt;
}Graph[MAXL << 1]; LL BIT[MAXL];
int head[MAXL], pos[MAXL], siz[MAXL];
int ch[MAXL][26], fail[MAXL], q[MAXL];
int ed[MAXN];
int N, K, tot, cnt, ID;
char S[MAXL];
bool inside[MAXN]; void update( int x, const int v ) { for( ; x <= ID ; up( x ) ) BIT[x] += v; }
LL getSum( int x ) { LL ret = 0; for( ; x ; down( x ) ) ret += BIT[x]; return ret; }
void update( const int x ) { if( ! inside[x] ) inside[x] = true, update( pos[ed[x]], 1 ), update( pos[ed[x]] + siz[ed[x]], -1 ); }
void remove( const int x ) { if( inside[x] ) inside[x] = false, update( pos[ed[x]], -1 ), update( pos[ed[x]] + siz[ed[x]], 1 ); } void addEdge( const int from, const int to )
{
Graph[++ cnt].to = to, Graph[cnt].nxt = head[from];
head[from] = cnt;
} void insert( const int rnk )
{
int p = 0, id;
for( int i = 1 ; S[i] ; i ++ )
{
id = S[i] - 'a';
if( ! ch[p][id] ) ch[p][id] = ++ tot;
p = ch[p][id];
}
ed[rnk] = p;
} void init()
{
int h = 1, t = 0, u, v;
Tour( i ) if( ch[0][i] ) q[++ t] = ch[0][i];
while( h <= t )
{
u = q[h ++];
Tour( i )
{
if( v = ch[u][i] ) fail[v] = ch[fail[u]][i], q[++ t] = v;
else ch[u][i] = ch[fail[u]][i];
}
addEdge( fail[u], u );
}
} void DFS( const int u )
{
siz[u] = 1, pos[u] = ++ ID;
for( int i = head[u], v ; i ; i = Graph[i].nxt )
DFS( v = Graph[i].to ), siz[u] += siz[v];
} int main()
{
LL ans; int id, p;
read( N ), read( K );
for( int i = 1 ; i <= K ; i ++ ) scanf( "%s", S + 1 ), insert( i );
init();
DFS( 0 );
for( int i = 1 ; i <= K ; i ++ ) update( i );
while( N -- )
{
scanf( "%s", S );
if( S[0] == '?' )
{
ans = p = 0;
for( int i = 1 ; S[i] ; i ++ )
p = ch[p][S[i] - 'a'],
ans += getSum( pos[p] );
write( ans ), putchar( '\n' );
}
else if( S[0] == '+' ) sscanf( S + 1, "%d", &id ), update( id );
else sscanf( S + 1, "%d", &id ), remove( id );
}
return 0;
}

[CF163E]e-Government的更多相关文章

  1. youths |government|some

    N-COUNT (新闻用语,尤指惹麻烦的)青年,小伙子Journalists often refer to young men as youths, especially when they are ...

  2. 题解-CF163E e-Government

    题面 CF163E e-Government 给 \(n\) 个字符串 \(s_i\) 和 \(q\) 个询问,刚开始字符串都服役.每次操作将集合中的一个字符串设为退役或服役,或查询与文本串 \(S_ ...

  3. 【CF163E 】e-Government

    题目 两个\(log\)的树状数组套树剖? 我们对于给出的\(n\)个模式串建立\(AC\)自动机,之后对于每一个询问串直接丢上去匹配 如果这里是暴力的话,我们直接一路跳\(fail\)累加作为结束位 ...

  4. 【NLP】Python NLTK获取文本语料和词汇资源

    Python NLTK 获取文本语料和词汇资源 作者:白宁超 2016年11月7日13:15:24 摘要:NLTK是由宾夕法尼亚大学计算机和信息科学使用python语言实现的一种自然语言工具包,其收集 ...

  5. UVA-146 ID Codes

    It is 2084 and the year of Big Brother has finally arrived, albeit a century late. In order to exerc ...

  6. 2011奥斯卡最佳纪录片《监守自盗(Inside Job)》小结

    影片探讨了2008年金融危机产生的原因. 美国忽略1933年的旧法律,立新法,以放松金融监管. 投资银行被允许更高的杠杆率,33:1,也就是说,投资物跌价3%就会导致破产. 投资银行放贷,但是转手将贷 ...

  7. 微服务(Microservices)—Martin Fowler【翻译】

    本文转载自:http://www.cnblogs.com/liuning8023/p/4493156.html -------------------------------------------- ...

  8. 资源描述结构(Resource Description Framework,RDF)

    资源描述框架(Resource Description Framework),一种用于描述Web资源的标记语言.RDF是一个处理元数据的XML(标准通用标记语言的子集)应用,所谓元数据,就是" ...

  9. 学券制(教育券、school voucher)

    美国「学券制」是怎样的一种制度?它为什么是共和党的执政政策?它在美国及其它地区有实施吗?效果如何?能否在保证公平的同时,通过市场提高教育质量? 作者:冉筱韬链接:https://www.zhihu.c ...

随机推荐

  1. Deno会在短期内取代Node吗?

    转载请注明出处:葡萄城官网,葡萄城为开发者提供专业的开发工具.解决方案和服务,赋能开发者. 原文出处:https://blog.bitsrc.io/what-is-deno-and-will-it-r ...

  2. HDU3117

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3117 题目大意:对于给定的一个数 n ,求斐波那契数F(n).对于超过八位的数,给出首末四位即可. 解 ...

  3. 容器技术之Docker网络

    上一篇博客我们主要聊了下docker镜像相关的说明以及怎样基于现有镜像制作镜像.分发镜像到docker仓库中的相关测试:回顾请参考https://www.cnblogs.com/qiuhom-1874 ...

  4. os.walk()的实际应用

    背景: 通过Mobaxterm从本地上传虹膜数据,一共79个类,每类里包含左右眼各400张数据,总共63200张,上传期间断网不确定是否传完. 思路: 1.首先遍历总类别数是否正确,若不足79,返回“ ...

  5. FPGA开发工具套餐搭配推荐及软件链接 (更新于2020.03.16)

    一.Xilinx(全球FPGA市场份额最大的公司,其发展动态往往也代表着整个FPGA行业的动态) (1) Xilinx官方软件下载地址链接: https://china.xilinx.com/supp ...

  6. solr学习(笔记) windows10+jdk1.8+tomcat8环境部署

    一:准备环境 1.1 »tomcat8.5下载地址:https://tomcat.apache.org/download-80.cgi 1.2 solr各版本下载地址:http://archive.a ...

  7. 永久关闭windows更新步骤

    在搜索“web和windows”框中输入“服务” 在搜索结果中点击第一个,那个图标像齿轮的那个!如下图. 在打开的“服务”窗口中,我们找到windows update   找到”windows upd ...

  8. 了解Lombok插件

    Lombok是什么 Lombok可以通过注解形式帮助开发人员解决POJO冗长问题,帮助构造简洁和规范的代码,通过注解可产生相应的方法. Lombok如何在IDEA中使用 我们都知道,使用一种工具,一定 ...

  9. 二、Spring装配Bean

    内容 声明bean 构造器注入和Setter方法注入 装配Bean 控制bean的创建和销毁 关键词 装配(wiring) 组件扫描(component scanning) 自动装配(AutoWiri ...

  10. 深度学习入门: CNN与LSTM(RNN)

    1. 理解深度学习与CNN: 台湾李宏毅教授的入门视频<一天搞懂深度学习>:https://www.bilibili.com/video/av16543434/ 其中对CNN算法的矩阵卷积 ...