对于一个字符串 S,我们定义 S 的分值 f(S)为 S 中出现的不同的字符个数。
例如f(“aba”)=2,f(“abc”)=3,f(“aaa”)=1。
现在给定一个字符串 S[0…n?1](长度为 n),请你计算对于所有 SS 的非空子串S[i…j] (0≤i≤j<n),f(S[i…j]) 的和是多少。
输入一行包含一个由小写字母组成的字符串 SS。
输出一个整数表示答案。
对于 20%20% 的评测用例,1≤n≤10;
对于 40%40% 的评测用例,1≤n≤100;
对于 50%50% 的评测用例,1≤n≤1000;
对于 60%60% 的评测用例,1≤n≤10000;
对于所有评测用例,1≤n≤100000。
ababc
28
分析
该题如果暴力枚举则是一个 O ( n 2 ) O(n^2) O(n2)的复杂度
很显然当n到10000时测评就很难通过
那么我们就要考虑一下有什么方法可以优化到 O ( n l o g n ) O(nlogn) O(nlogn), O ( n ) O(n) O(n)以内举例
按样例的列举如下图划分,我们就可以将本题转换成一个计算每个字符贡献的情况
①先举一个没有重复的例子,他的每个字母出现的次数
s[i]:a b c d e
f[i]:5 8 9 8 5
有没有看出什么,没有?那我们再细分
1*5 2*4 3*3 4*2 5*1
是不是看出了些什么(#.#)
②再来看一个有重复了例子
s[i]:a b a b c
f[i]:5 8 6 4 5
如下图所示第3个位置a出现了三段,与一段与第1个位置a发生了重复(舍去[ f[i] * 1/3 ])
如下图所示第4个位置a出现了三段,与两段与第2个位置a发生了重复(舍去[ f[i] * 2/4 ])
那么我么只需开一个数组last[]记录上一个字母s[i]出现的最后位置即可知道多少位置发生重复
重复a 3:(9-91/3)
重复b 4:(8-82/4)推公式
重复s[i]: f[i] - f[i] / i*last[s[i]]
子串 f值
a 1
ab 2
aba 2
abab 2
ababc 3
b 1
ba 2
bab 2
babc 3
a 1
ab 2
abc 3
b 1
bc 2
c 1
#include<iostream>
#include<cstring>
using namespace std;
typedef long long ll;
const int N = 1e5+10;
char s[N];
ll f[N]; //预处理会爆int
int last[30];
int main(){
scanf("%s",s+1);
int n = strlen(s+1);
ll ans = 0;
//预处理没有任何重复的情况;
for(int i=1;i<=n-i+1;i++)f[i] = f[n-i+1] = (n-i+1)*(ll)i; //注意乘的时候一定要转long long
//统计总贡献,并去重
for(int i = 1;i<=n;i++){
int t = s[i]-'a';
if(!last[t]){ //判断有无重复部分
ans += f[i];
}else{
ans += f[i] - f[i]/i*last[t]; //减去重复部分;
}
last[t] = i; //记录当前字母最后出现位置
}
printf("%lld",ans);
return 0;
}
Elasticsearch 是通过 Lucene 的倒排索引技术实现比关系型数据库更快的过滤。特...
DELETEFROMTablesWHEREIDNOTIN(SELECTMin(ID)FROMTablesGROUPBYName) Min的话保...
4月11日20:30~22:00通过腾讯会议进行了第二次在线学习讨论我把学习笔记整理一下...
正则忽略大小写 – RegexOptions.IgnoreCase 例如: 复制代码 代码如下: Str = R...
项目中用到的一些特殊字符和图标 html代码 XML/HTML Code 复制内容到剪贴板 div ...
复制代码 代码如下: % URL="http://news.163.com/special/00011K6L/rss_newstop....
本文实例讲述了Laravel框架源码解析之反射的使用。分享给大家供大家参考,具体如...
错误描述: 在开发.net项目中,通过microsoft.ACE.oledb读取excel文件信息时,报...
上篇文章给大家介绍了 Java正则表达式匹配,替换,查找,切割的方法 ,接下来,...
工具:Eclipse,Oracle,smartupload.jar;语言:jsp,Java;数据存储:Oracle。...