bzoj1563: [NOI2009]诗人小G
Description
Input
Output
对于每组数据,若最小的不协调度不超过1018,则第一行一个数表示不协调度若最小的不协调度超过1018,则输出"Too hard to arrange"(不包含引号)。每个输出后面加"--------------------"
Sample Input
4
4 9 3
brysj,
hhrhl.
yqqlm,
gsycl.
4 9 2
brysj,
hhrhl.
yqqlm,
gsycl.
1 1005 6
poet
1 1004 6
poet
4 9 3
brysj,
hhrhl.
yqqlm,
gsycl.
4 9 2
brysj,
hhrhl.
yqqlm,
gsycl.
1 1005 6
poet
1 1004 6
poet
Sample Output
108
--------------------
32
--------------------
Too hard to arrange
--------------------
1000000000000000000
--------------------
【样例说明】
前两组输入数据中每行的实际长度均为6,后两组输入数据每行的实际长度均为4。一个排版方案中每行相邻两个句子之间的空格也算在这行的长度中(可参见样例中第二组数据)。每行末尾没有空格。
--------------------
32
--------------------
Too hard to arrange
--------------------
1000000000000000000
--------------------
【样例说明】
前两组输入数据中每行的实际长度均为6,后两组输入数据每行的实际长度均为4。一个排版方案中每行相邻两个句子之间的空格也算在这行的长度中(可参见样例中第二组数据)。每行末尾没有空格。
HINT
总共10个测试点,数据范围满足:
测试点 T N L P
1 ≤10 ≤18 ≤100 ≤5
2 ≤10 ≤2000 ≤60000 ≤10
3 ≤10 ≤2000 ≤60000 ≤10
4 ≤5 ≤100000 ≤200 ≤10
5 ≤5 ≤100000 ≤200 ≤10
6 ≤5 ≤100000 ≤3000000 2
7 ≤5 ≤100000 ≤3000000 2
8 ≤5 ≤100000 ≤3000000 ≤10
9 ≤5 ≤100000 ≤3000000 ≤10
10 ≤5 ≤100000 ≤3000000 ≤10
所有测试点中均满足句子长度不超过30。
题解:
https://www.byvoid.com/blog/noi-2009-poet
code:
1 #include<cstdio> 2 #include<iostream> 3 #include<cmath> 4 #include<cstring> 5 #include<algorithm> 6 using namespace std; 7 char ch; 8 bool ok; 9 void read(int &x){ 10 for (ok=0,ch=getchar();!isdigit(ch);ch=getchar()) if (ch=='-') ok=1; 11 for (x=0;isdigit(ch);x=x*10+ch-'0',ch=getchar()); 12 if (ok) x=-x; 13 } 14 typedef long double int64; 15 const int maxn=100005; 16 const int maxl=3000005; 17 const int64 maxval=1E18; 18 char s[maxl]; 19 int T,n,l,p; 20 int64 sum[maxn],f[maxn]; 21 bool flag; 22 int64 ksm(int64 a,int b){ 23 int64 t; 24 for (t=1;b;a*=a,b>>=1) if (b&1) t*=a; 25 return t; 26 } 27 int64 calc(int j,int i){return f[j]+ksm(abs(sum[i]-sum[j]+i-j-1-l),p);} 28 struct Stack{ 29 int top,pos; 30 struct Data{ 31 int st,ed,id; 32 }s[maxn],tmp; 33 void init(){s[top=1]=(Data){1,n,0},pos=1;} 34 bool cmp(int t,int x,int y){return calc(x,t)<calc(y,t);} 35 int get(int id){ 36 int l=tmp.st,r=tmp.ed,m,a=tmp.id; 37 while (l<r){ 38 m=((l+r)>>1)+1; 39 if (cmp(m,a,id)) l=m; else r=m-1; 40 } 41 return l; 42 } 43 void push(int id){ 44 while (top&&!cmp(s[top].st,s[top].id,id)) top--; 45 tmp=s[top--]; 46 int m=get(id); 47 if (tmp.st<=m) s[++top]=(Data){tmp.st,m,tmp.id}; 48 if (m<n) s[++top]=(Data){m+1,n,id}; 49 } 50 int64 query(int x){ 51 while (x>s[pos].ed) pos++; 52 return calc(s[pos].id,x); 53 } 54 }stack; 55 int main(){ 56 for (read(T);T;T--){ 57 read(n),read(l),read(p); 58 for (int i=1;i<=n;i++) scanf("%s",s+1),sum[i]=sum[i-1]+strlen(s+1); 59 stack.init(),flag=0; 60 for (int i=1;i<=n;i++){ 61 f[i]=stack.query(i); 62 stack.push(i); 63 } 64 if (f[n]>maxval) puts("Too hard to arrange"); 65 else printf("%lld\n",(long long)f[n]); 66 puts("--------------------"); 67 } 68 return 0; 69 }