在一个操场上摆放着一排N堆石子。现要将石子有次序地合并成一堆。规定每次只能选相邻的2堆石子合并成新的一堆,并将新的一堆石子数记为该次合并的得分。
试设计一个算法,计算出将N堆石子合并成一堆的最小得分。
标签:
共一个数,即N堆石子合并成一堆的最小得分。
对于 100% 的数据,1≤N≤40000
对于 100% 的数据,1≤A≤200
接下来是嘴巴时间!!
1 #include<iostream> 2 #include<cstdio> 3 #include<cstdlib> 4 #include<cmath> 5 #include<algorithm> 6 #define yyj(s) freopen(s".in","r",stdin),freopen(s".out","w",stdout); 7 #define llg long long 8 #define maxn 40010 9 llg i,j,k,x,n,m,a[maxn],ans; 10 using namespace std; 11 llg get() 12 { 13 llg i=0; char c=getchar(); 14 while(c>‘9‘||c<‘0‘)c=getchar(); 15 while(c>=‘0‘&&c<=‘9‘)i=i*10+c-‘0‘,c=getchar(); 16 return i; 17 } 18 19 int main() 20 { 21 yyj("a"); 22 cin>>n; 23 for (i=1;i<=n;i++) a[i]=get(); 24 a[0]=a[n+1]=0x7fffffff; 25 for (m=1;m<n;m++) 26 { 27 a[n-m+2]=0x7fffffff; 28 for (k=2;k<=n-m+1;k++) if (a[k-1]<=a[k+1]) break; 29 x=a[k-1]+a[k]; ans+=x; 30 for (i=k-1;i<=n-m;i++) a[i]=a[i+2]; 31 for (j=k-2;j>=0;j--) if (a[j]>x) break; 32 for (i=n-m;i>j+1;i--) a[i]=a[i-1]; 33 a[j+1]=x; 34 } 35 cout<<ans; 36 return 0; 37 }
你以为这可以A?这只是一发常数写大了超时的
当你把常数写小
1548112 | xrdog | 3229 | 正确 | 1484 kb | 60 ms | C++/Edit | 1080 B | 2016-07-14 20:13:13 |
标签:
原文地址:http://www.cnblogs.com/Dragon-Light/p/5671762.html