题意

给出n个字符串,每个字符串有一个权值wi 有q个操作,操作有两种 1 x y 将字符串x的权值变为y 2 x 查询操作,输出以字符串x为后缀,且权值小于等于wx的字符串个数。其中n<=1000 每个字符串长度<=1000 询问q<=80000。

分析

n并不大,但是q太大了。如果暴力的话,每次查询都是o(n*len)的,肯定不行。

等等,谁说不行?我试试 emmm。。。爆过去了????下面是瞎几把爆的代码:

 #include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm> using namespace std;
const int maxn=+;
int len[maxn],w[maxn];
char s[maxn][maxn];
int T,n,q; int main(){
scanf("%d",&T);
for(int t=;t<=T;t++){
scanf("%d",&n);
for(int i=;i<=n;i++){
scanf("%s",s[i]);
scanf("%d",&w[i]);
len[i]=strlen(s[i]);
}
scanf("%d",&q);
int opt;
for(int i=;i<=q;i++){
scanf("%d",&opt);
if(opt==){
int x,y;
scanf("%d%d",&x,&y);
w[x]=y;
}else if(opt==){
int x;
scanf("%d",&x);
int ans=;
for(int j=;j<=n;j++){
if(w[j]>w[x])continue;
if(len[j]<len[x])continue;
bool ok=;
for(int k=len[j]-,l=len[x]-;l>=;k--,l--){
if(s[x][l]!=s[j][k]){
ok=;
break;
}
}
if(ok){
ans++;
// cout<<j<<endl;
}
}
printf("%d\n",ans);
}
}
}
return ;
}

好吧好吧,上面那个不算,我们重新来想···

后缀嘛,后缀数组?咳,我就知道名字而已不会。。想点会的。。

字典树行不行?我们只要把字符串倒着插进去就可以用统计前缀的方法来统计后缀了。

w这个限制怎么办?

我们在字典树上每一个字符串结尾维护一个vector···这样··时间复杂度是多少?均摊下应该是···可以的···吧?

 #include <cstdio>
#include <cstring>
#include <algorithm>
#include <iostream>
#include <vector>
using namespace std;
const int maxn=+;
int ch[maxn*maxn][],W[maxn];
char s[maxn][maxn];
int val[maxn*maxn];
vector<int>G[maxn*maxn];
int T,n,q,sz;
void insert(char *s,int w){
int len=strlen(s);
int u=;
for(int i=;i<len;i++){
int id=s[i]-'a';
if(!ch[u][id]){
ch[u][id]=++sz;
}
u=ch[u][id];
}
G[u].push_back(w);
return ;
}
void tra(int u){
/* if(G[u].size()!=0){
for(int i=0;i<G[u].size();i++){
printf("%d ",G[u][i]);
}
return;
}*/
for(int i=;i<;i++){
if(ch[u][i]){
printf("%c",i+'a');
tra(ch[u][i]);
}
}
return;
}
int ans;
void check(int u,int k){
if(G[u].size()){
for(int i=;i<G[u].size();i++){
if(W[G[u][i]]<=W[k]){
ans++;
}
}
}
for(int i=;i<;i++){
if(ch[u][i])
check(ch[u][i],k);
}
return;
}
void solve(int k){
int u=;
ans=;
for(int i=strlen(s[k])-;i>=;i--){
int id=s[k][i]-'a';
if(!ch[u][id]){
return ;
}
u=ch[u][id];
}
check(u,k);
return ;
}
int main(){
scanf("%d",&T);
for(int t=;t<=T;t++){
scanf("%d",&n);
for(int i=;i<=*;i++)G[i].clear();
memset(val,,sizeof(val));
memset(ch,,sizeof(ch));
sz=;
char s1[maxn];
int x;
for(int i=;i<=n;i++){
scanf("%s%d",s[i],&W[i]);
for(int j=;j<strlen(s[i]);j++){
s1[j]=s[i][strlen(s[i])--j];
}
s1[strlen(s[i])]='\0';
insert(s1,i);
}
// tra(0); scanf("%d",&q);
for(int i=;i<=q;i++){
int opt;
scanf("%d",&opt);
if(opt==){
int x,y;
scanf("%d%d",&x,&y);
W[x]=y;
}else if(opt==){
int x;
scanf("%d",&x);
solve(x);
printf("%d\n",ans);
}
}
}
return ;
}

【FZU2280】Magic的更多相关文章

  1. 【POJ2888】Magic Bracelet Burnside引理+欧拉函数+矩阵乘法

    [POJ2888]Magic Bracelet 题意:一个长度为n的项链,有m种颜色的珠子,有k个限制(a,b)表示颜色为a的珠子和颜色为b的珠子不能相邻,求用m种珠子能串成的项链有多少种.如果一个项 ...

  2. 【CF878D】Magic Breeding bitset

    [CF878D]Magic Breeding 题意:有k个物品,每个物品有n项属性值,第i个人的第j个属性值为aij,有q个操作: 1 x y 用x和y合成一个新的物品,新物品的编号是++k,新物品的 ...

  3. 【CF628D】Magic Numbers 数位DP

    [CF628D]Magic Numbers 题意:求[a,b]中,偶数位的数字都是d,其余为数字都不是d,且能被m整除的数的个数(这里的偶数位是的是从高位往低位数的偶数位).$a,b<10^{2 ...

  4. 【hihocoder】 Magic Box

    题目1 : Magic Box 时间限制:10000ms 单点时限:1000ms 内存限制:256MB 描述 The circus clown Sunny has a magic box. When ...

  5. 【CF1110E】 Magic Stones - 差分

    题面 Grigory has n n magic stones, conveniently numbered from \(1\) to \(n\). The charge of the \(i\)- ...

  6. 【CF632F】Magic Matrix(生成树 脑洞)

    题目链接 大意 给定一个\(N\times N\)的矩阵,问是否满足以下三个条件: \(A_{i,i}=0\) \(A_{i,j}=A_{j,i}\) 对于任意的\(i,j,k\),满足\(A_{i, ...

  7. 【xsy1232】Magic 最小割

    题目大意:给你一个$n$个点,$m$条有向边的图,每个点有一个点权$a_i$,同时你可以用$b_i$的代价将$a_i$变为$0$ 另外你要付出$\sum\limits_{i=1}^n\max\limi ...

  8. 【ZOJ4061】Magic Multiplication(构造)

    题意:定义一个新运算为两个数A,B上每一位相乘,然后顺次接在一起,现在给定结果C和原来两个数字的长度,要求恢复成原来的数字A,B 若有多解输出A字典序最小的,A相同输出B字典序最小的,无解输出Impo ...

  9. 【Codeforces1117C_CF1117C】Magic Ship(构造)

    题目: Codeforces1117C 考的时候很困,开局半小时后才过A,只做出来AB,排名3000+,掉了119--半夜体验极差. 翻译: 你是一个船长.最初你在点 \((x_1,y_1)\) (显 ...

随机推荐

  1. 专业工具软件AutoCAD复习资料

    专业工具软件AutoCAD复习资料 下载地址:http://download.csdn.net/detail/zhangrelay/9849503 这里给出了一些dwg格式的CAD资料,用于课后学习和 ...

  2. linux多线程全面解析

      引入:     在传统的Unix模型中,当一个进程需要由另一个实体执行某件事时,该进程派生(fork)一个子进程,让子进程去进行处理.Unix下的大多数网络服务器程序都是这么编写的,即父进程接受连 ...

  3. 《Ubuntu入门基础》第三篇

    创建虚拟磁盘

  4. iOS当前屏幕截屏

    需求描述: 有两个ViewController 我们记做 A.B ,其中B controller只是显示下半部分: 如下图效果: 实现这种的方案很多,可以用添加View方法,  也可以用UIWindo ...

  5. Instruments检测解决内存泄露以及进行性能测试

    1.启动Xcode自带的Instruments.这里有两种方法启动. 方法一: 方法二: 2.选择Leaks选项.(该选项用来进行内存泄漏检测) 说明: Leaks:找到引发内存泄漏的起点. Time ...

  6. 【spring源码学习】spring的事件发布监听机制源码解析

    [一]相关源代码类 (1)spring的事件发布监听机制的核心管理类:org.springframework.context.event.SimpleApplicationEventMulticast ...

  7. 【BZOJ2908】又是nand 树链剖分+线段树

    [BZOJ2908]又是nand escription 首先知道A nand B=not(A and B) (运算操作限制了数位位数为K)比如2 nand 3,K=3,则2 nand 3=not (2 ...

  8. IDC单IP绑定多域名(包括端口)

    本文件已上传到文件列表中. ServerName 222.186.36.116:80 DocumentRoot "/home" <Directory "/home& ...

  9. SpringBean生命周期

    Spring作为当前Java最流行.最强大的轻量级框架,受到了程序员的热烈欢迎.准确的了解Spring Bean的生命周期是非常必要的.我们通常使用ApplicationContext作为Spring ...

  10. Java调用Groovy

    记录一下 http://docs.groovy-lang.org/latest/html/documentation/guide-integrating.html