http://codeforces.com/gym/101138/problem/A

感觉有一种套路就是总长度 <= 某一个数的这类题,大多可以分块

首先把集合串按长度分块,对于每一个询问串,

在 > magic的big集合里,因为最多sqrtn个,可以暴力枚举每一个,然后暴力枚举询问串的每一个长度是其的子串,判断是否相等

在 <= magic的small集合里,枚举每一个长度是magic, magic-1, magic-2, magic-3........1的字符串,然后看看是否在small集合里存在

small集合用unordermap保存即可。

ps

判断map是否存在一个元素,用mp.find

不然用mp[]每次都会生成一个节点,然后MLE, 清空用mp.erase

不然Mp.find是true的

#include <bits/stdc++.h>
#define IOS ios::sync_with_stdio(false)
using namespace std;
#define inf (0x3f3f3f3f)
typedef unsigned long long int ULL; const int seed = ;
const int maxn = + ;
struct Node {
ULL hs;
int lenstr;
Node(ULL _hs, int _lenstr) {
hs = _hs, lenstr = _lenstr;
}
bool operator < (const Node & rhs) const {
if (hs != rhs.hs) return hs > rhs.hs;
else return lenstr > rhs.lenstr;
}
};
vector<Node> all;
set<Node> ss;
unordered_map<ULL, bool> mp;
char str[maxn];
int magic;
set<Node> :: iterator it;
void addchar(int id, char ch) {
// set<Node> :: iterator it;
if (all[id].lenstr > magic) {
ss.erase(ss.find(all[id]));
all[id].lenstr++;
all[id].hs = all[id].hs * seed + ch;
ss.insert(all[id]);
} else {
if (all[id].lenstr == magic) {
mp.erase(all[id].hs);
// mp[all[id].hs] = false;
all[id].lenstr++;
all[id].hs = all[id].hs * seed + ch;
ss.insert(all[id]);
} else {
mp.erase(all[id].hs);
all[id].lenstr++;
all[id].hs = all[id].hs * seed + ch;
mp[all[id].hs] = true;
}
}
}
ULL po[maxn];
ULL sum[maxn];
int last_yes;
bool ok() {
int lenstr = strlen(str + );
for (int i = ; i <= lenstr; ++i) {
str[i] = (str[i] - 'a' + last_yes) % + 'a';
sum[i] = sum[i - ] * seed + str[i];
}
for (it = ss.begin(); it != ss.end(); ++it) {
int len = it->lenstr;
for (int j = len; j <= lenstr; ++j) {
if (it->hs == sum[j] - po[len] * sum[j - len]) return true;
}
}
for (int i = ; i <= lenstr; ++i) {
for (int c = ; c <= magic && c <= i; ++c) {
if (mp.find(sum[i] - po[c] * sum[i - c]) != mp.end()) return true;
}
}
return false;
} void work() {
int n, q;
scanf("%d%d", &n, &q);
magic = (int)sqrt(n * 1.0);
for (int i = ; i <= n; ++i) {
scanf("%s", str + );
ULL hashVal = ;
int lenstr = strlen(str + );
for (int j = ; j <= lenstr; ++j) {
hashVal = hashVal * seed + str[j];
}
if (lenstr > magic) ss.insert(Node(hashVal, lenstr));
else {
mp[hashVal] = true;
}
all.push_back(Node(hashVal, lenstr));
}
last_yes = ;
for (int i = ; i < q; ++i) {
int op;
scanf("%d", &op);
if (op == ) {
int index, ch;
scanf("%d%d", &index, &ch);
addchar((index + last_yes) % n, (ch + last_yes) % + 'a');
} else {
scanf("%s", str + );
if (ok()) {
printf("YES\n");
last_yes = i;
} else printf("NO\n");
}
}
} int main() {
#ifdef local
freopen("data.txt", "r", stdin);
// freopen("data.txt", "w", stdout);
#endif
po[] = ;
for (int i = ; i <= maxn - ; ++i) po[i] = po[i - ] * seed;
work();
return ;
}

A. Yet Another Problem with Strings 分块 + hash的更多相关文章

  1. Codeforces Round #FF (Div. 2):Problem A - DZY Loves Hash

    A. DZY Loves Hash time limit per test 1 second memory limit per test 256 megabytes input standard in ...

  2. hdu_5085_Counting problem(莫队分块思想)

    题目连接:hdu_5085_Counting problem 题意:给你一个计算公式,然后给你一个区间,问这个区间内满足条件的数有多少个 题解:由于这个公式比较特殊,具有可加性,我们考虑讲一个数分为两 ...

  3. POJ 3468 A Simple Problem with Integers(分块入门)

    题目链接:http://poj.org/problem?id=3468 A Simple Problem with Integers Time Limit: 5000MS   Memory Limit ...

  4. Educational Codeforces Round 69 (Rated for Div. 2) D. Yet Another Subarray Problem 【数学+分块】

    一.题目 D. Yet Another Subarray Problem 二.分析 公式的推导时参考的洛谷聚聚们的推导 重点是公式的推导,推导出公式后,分块是很容易想的.但是很容易写炸. 1 有些地方 ...

  5. POJ3468 a simple problem with integers 分块

    题解:分块 解题报告: 是个板子题呢qwq 没什么可说的,加深了对分块的理解趴还是 毕竟这么简单的板子题我居然死去活来WA了半天才调出来,,,哭了QAQ 还是说下我错在了哪几个地方(...是的,有好几 ...

  6. CF985F Isomorphic Strings (字符串Hash,巧解)

    题目链接 题意翻译 给你一个长度为 \(n\) 的字符串,\(m\) 次询问. 问两个相同长度的子串是否匹配. 我们称两个子串是匹配的,当且仅当其满足: 其中一个子串的字母可替代另一个子串的字母 例如 ...

  7. POJ 3468 A Simple Problem with Integers (分块)

    Description You have \(N\) integers, \(A_1, A_2, ... , A_N\). You need to deal with two kinds of ope ...

  8. CodeForces 165C Another Problem on Strings(组合)

    A string is binary, if it consists only of characters "0" and "1". String v is a ...

  9. Day8 - C - Another Problem on Strings CodeForces - 165C

    A string is binary, if it consists only of characters "0" and "1". String v is a ...

随机推荐

  1. python常见的加密解密

    #!/usr/bin/env python ''' Python Crypto Wrapper - By Chase Schultz Currently Supports: AES-256, RSA ...

  2. jQuery+css实现tab功能

    点击我我会消失 Click me 点击按钮我会消失,再点击我会出现 演示tab tab1 tab2 tab3 [环球时报记者 郭芳] “中国秘密发射新快速响应火箭”,25日,在中国官方媒体报道我国“快 ...

  3. 【zookeeper】

    window下安装zookeeper三结点集群: 1:解压缩zookeeper压缩包:复制三分并且命名成:Server_A   Server_B  Server_C 2:拷贝conf目录下的文件zoo ...

  4. 从一个xaml文件获取xaml内容,遍历寻找对象

  5. JetBrains Rider 在 Mac 环境下将 cs 文件生成 exe

    因为自己的开发环境是 Mac + Rider 组合,想测试网络编程相关内容.想在Windows 虚拟机上运行一套代码来与Mac 机进行测试,但又不想在虚拟机上安装一套开发环境.最终找到的解决方案是通过 ...

  6. 理解JavaScript普通函数以及箭头函数里使用的this

    this 普通函数的this 普通函数的this是由动态作用域决定,它总指向于它的直接调用者.具体可以分为以下四项: this总是指向它的直接调用者, 例如 obj.func() ,那么func()里 ...

  7. python logging日志库

    项目中使用的日志库是使用python官方库logging封装的,但是居然一直么有设置日志自动滚动,经常会受到告警说哪台机器磁盘空间又满,清理一下,于是研究一下,解决这个问题. 参考:https://d ...

  8. Unity苹果(iOS)内购接入(Unity内置IAP)

    https://www.jianshu.com/p/4045ebf81a1c Unity苹果(iOS)内购接入(Unity内置IAP) Kakarottog                       ...

  9. LINQ和Lambda表达式

    前言 前段时间接触了一种新的表达式,但是不知道这个是什么意思,所以就先站在巨人的肩膀用了,现在听师哥说这种写法是Lambda表达式.我一直以为,这个Lambda表达式和LINQ查询有异曲同工之妙,可惜 ...

  10. luogu P3811线性求逆元

    首先扩O:T了一个点(因为上界松),83分. #include <cstdio> using namespace std; int n, p; void exgcd(int a, int ...