HDU4436---str2int 后缀树组(12年天津区域赛)
str2int
Time Limit: 6000/3000 MS (Java/Others) Memory Limit: 131072/131072 K (Java/Others)
Total Submission(s): 1568 Accepted Submission(s): 540
An example is shown below.
101
123
The set S of strings is consists of the N strings given in the input file, and all the possible substrings of each one of them.
It's boring to manipulate strings, so you decide to convert strings in S into integers.
You can convert a string that contains only digits into a decimal integer, for example, you can convert "101" into 101, "01" into 1, et al.
If an integer occurs multiple times, you only keep one of them.
For example, in the example shown above, all the integers are 1, 10, 101, 2, 3, 12, 23, 123.
Your task is to calculate the remainder of the sum of all the integers you get divided by 2012.
The test case starts by a line contains an positive integer N.
Next N lines each contains a string consists of one or more digits.
It's guaranteed that 1≤N≤10000 and the sum of the length of all the strings ≤100000.
The input is terminated by EOF.
101
123
09
000
1234567890
题意: n个字符串,对于每一个子串可以表示为一个数字, 求所有子串的数字和相加对2012取模,, 相同数字只算一次。
这题可以先把n个字符串用一个没有出现过的字符隔开连起来。然后求sa, lcp。
我们可以先看一个简单的例子。
s = 12345
num[1] = 1 sum[1] = 1
num[2] = 12 sum[2] = 1 + 12
num[3] = 123 sum[3] = 1 + 12 + 123
num[4] = 1234 sum[4] = 1 + 12 + 123 + 1234
num[5] = 12345 sum[5] = 1 + 12 + 123 + 1234 + 12345
如果求[3, 4] , 只需要 sum[5] - sum[2] - num[2] * (10 + 100 + 1000);
判重时 只要从 i+ lcp[rank[i]] 开始算就可以了,,因为公共前缀那一部分 在前面已经算了。
上代码。。
#include <set>
#include <map>
#include <cmath>
#include <ctime>
#include <queue>
#include <stack>
#include <cstdio>
#include <string>
#include <vector>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std;
typedef unsigned long long ull;
typedef long long ll;
const int inf = 0x3f3f3f3f;
const double eps = 1e-;
const int mod = ;
const int maxn = 2e5+;
int sum [maxn], num[maxn];
string s;
int sa[maxn], Rank[maxn], tmp[maxn], lcp[maxn];
int k, len;
bool cmp(int i, int j)
{
if (Rank[i] != Rank[j])
return Rank[i] < Rank[j];
else
{
int x = (i+k <= len ? Rank[i+k] : -);
int y = (j+k <= len ? Rank[j+k] : -);
return x < y;
}
}
void build_sa()
{
for (int i = ; i <= len; i++)
{
sa[i] = i;
Rank[i] = (i < len ? s[i] : -);
}
for (k = ; k <= len; k *= )
{
sort (sa,sa+len+,cmp);
tmp[sa[]] = ;
for (int i = ; i <= len; i++)
{
tmp[sa[i]] = tmp[sa[i-]] + (cmp(sa[i-],sa[i])? : );
}
for (int i = ; i <= len; i++)
Rank[i] = tmp[i];
}
} void Get_lcp()
{
for (int i = ; i < len; i++)
Rank[sa[i]] = i;
int h = ;
lcp[] = ;
for (int i = ; i < len; i++)
{
int j = sa[Rank[i]-];
if (h > )
h--;
for (; h+i < len && h+j < len; h++)
if (s[i+h] != s[j+h])
break;
lcp[Rank[i]] = h;
}
}
bool isdigit(char &ch)
{
return ch >= '' && ch <= '';
}
int vec[maxn], board[maxn], tot;
int SUM[maxn];
int solve (int l, int r)
{
if (l > r)
return ;
int res ;
res = sum[r] - sum[l-];
res = ((res%mod)+mod)%mod;
res -= num[l-] * SUM[r-l+];
res = ((res%mod)+mod)%mod;
return ((res%mod)+mod)%mod;
}
int main()
{
#ifndef ONLINE_JUDGE
freopen("in.txt","r",stdin);
#endif
int n;
SUM[] = ;
for (int i = ; i < maxn; i++)
{
SUM[i] = (SUM[i-] + ) * % mod;
}
while (~scanf ("%d", &n))
{
s = "\0";
tot = ;
memset(sum, , sizeof(sum));
memset(num, , sizeof(num));
for (int i = ; i < n; i++)
{
string tmp;
cin >> tmp;
s += tmp + "#";
}
len = s.size();
int val = ;
for (int i = ; i < len; i++)
{
if (s[i] != '#')
{
val = (val * + s[i] - '') % mod;
num[i] = val;
sum[i] = (sum[i-] + num[i]) % mod;
board[i] = tot;
}
if (s[i] == '#')
{
vec[tot++] = i;
num[i] = val;
sum[i] = sum[i-] + val;
}
}
build_sa();
Get_lcp();
int ans = ;
for (int i = ; i < len; i++)
{
int t1 = i + lcp[Rank[i]];
if (s[i] == '')
continue;
if (isdigit(s[i]) && i+lcp[Rank[i]] < vec[board[i]])
{
int t2 = vec[board[i]] -;
int ans1 = solve(i, t2);
int ans2 = solve(i , t1-);
ans = (ans + solve(i, t2) - solve(i, t1-)) % mod;
if (ans < )
ans += mod;
}
}
printf("%d\n", ans%mod);
}
return ;
}
HDU4436---str2int 后缀树组(12年天津区域赛)的更多相关文章
- 【BZOJ-1396&2865】识别子串&字符串识别 后缀自动机/后缀树组 + 线段树
1396: 识别子串 Time Limit: 10 Sec Memory Limit: 162 MBSubmit: 312 Solved: 193[Submit][Status][Discuss] ...
- FZU 2137 奇异字符串 后缀树组+RMQ
题目连接:http://acm.fzu.edu.cn/problem.php?pid=2137 题解: 枚举x位置,向左右延伸计算答案 如何计算答案:对字符串建立SA,那么对于想双延伸的长度L,假如有 ...
- SPOJ694 -- DISUBSTR 后缀树组求不相同的子串的个数
DISUBSTR - Distinct Substrings Given a string, we need to find the total number of its distinct su ...
- POJ3581---Sequence 后缀树组
题意:n个数字组成的序列,第一个数字最大,,把序列分成3部分,每个部分分别翻转,输出翻转后字典序最小的序列.. 后缀数组变一下,,先求出 第一个分割的位置,,然后再求一次后缀数组,,求出第二个位置.. ...
- CF504E Misha and LCP on Tree(树链剖分+后缀树组)
1A真舒服. 喜闻乐见的树链剖分+SA. 一个初步的想法就是用树链剖分,把两个字符串求出然后hash+二分求lcp...不存在的. 因为考虑到这个字符串是有序的,我们需要把每一条重链对应的字符串和这个 ...
- [hdu4436 str2int]后缀自动机SAM(或后缀数组SA)
题意:给n个数字串,求它们的所有不包含前导0的不同子串的值之和 思路:把数字串拼接在一起,构造SAM,然后以每个状态的长度len作为特征值从小到大排序,从前往后处理每个状态,相当于按拓扑序在图上合并计 ...
- 【2012天津区域赛】部分题解 hdu4431—4441
1001: 题意:给你13张麻将牌,问可以胡哪些张 思路: 枚举可能接到的牌,然后dfs判断能否胡 1002: 题意: 已知n,m 求 n的所有约数在m进制下的平方和 做法:队长用java高精度写的 ...
- ACM学习历程——HDU4472 Count(数学递推) (12年长春区域赛)
Description Prof. Tigris is the head of an archaeological team who is currently in charge of an exca ...
- ACM学习历程——HDU4814 Golden Radio Base(数学递推) (12年成都区域赛)
Description Golden ratio base (GRB) is a non-integer positional numeral system that uses the golden ...
随机推荐
- Windows消息传递机制具体解释
林炳文Evankaka原创作品.转载请注明出处http://blog.csdn.net/evankaka Windows是一个消息(Message)驱动系统.Windows的消息提供了应用程序之间.应 ...
- Jetty开发指导:框架
Spring设置 你能嵌入Jetty到你的项目中,也能够使用差点儿全部的IoC类型框架,包含Spring.假设全部你想做的是在你的Spring中设置Jetty Server,那么以下的xml片段能够作 ...
- Java Performance Optimization Tools and Techniques for Turbocharged Apps--reference
Java Performance Optimization by: Pierre-Hugues Charbonneau reference:http://refcardz.dzone.com/refc ...
- Environment Configuration Files
Environment Configuration Files When a user logs in, an environment is created for that user automat ...
- linux定时任务2-at命令
定时执行命令: [root@rheltest1 ~]# at now + 1 minute //一分钟后执行下面的任务 at> date >> /tmp/test_date.log ...
- Spring MVC 时间字符串 @PathVariable获取
@PathVariable("date") @DateTimeFormat(pattern="yyyy-MM-dd") Date date
- 自定义圆形imageview
import android.content.Context; import android.graphics.Bitmap; import android.graphics.BitmapShader ...
- 启用DHCP中继代理,实现跨子网服务 - Win 2003 Server
伴随着局域网规模的逐步扩大,一个网络常常会被划分成多个不同的子网,以便根据不同子网的工作要求来实现个性化的管理要求.考虑到规模较大的局域网一般会使用DHCP服务器来为各个工作站分配IP地址,不过一旦局 ...
- C++拾遗(六)函数相关(1)
返回值 C++规定返回值不能是 数组.但可以是其它任何类型(包括结构体和对象). 通常,函数将返回值复制到指定的CPU寄存器或内存单元中,然后调用函数调用该内存单元的值. 函数原型 参数列表中可以不包 ...
- deb文件安装命令
一般在此类发行版中可以直接双击安装 手动安装.如果您喜欢使用终端,您需要管理员权限来安装一个 .deb 文件. 打开终端后,输入: sudo dpkg -i package_file.deb 要卸载一 ...