这是2018与2013提高组的真题,可怕,,原题出了两年,是个纯模拟。
读完题后就想写一个朴素的模拟,先遍历层数,再把达到层数的宽度#存起来,再判断是否连续,如果不连续ans++,然后每一次循环都要初始化,所以第一次提交得了80pts,TLE了最后两个点。然后再去看题解,竟然发现:当i+1组数据大于i组数据,ans+=h[i+1]-h[i],因为只要小于就是前面的最大的操作数,然后因为不连续所以即使大于前面的但小于前面最大ans也需要++。
1.思路清晰,对时间复杂度进行计算,10^5for来for去再加memset一般就超时了
2.模拟题还是需要找找性质,找到最优的解题方法,简单的题要追求满分
代码1(80‘):
1 #include<iostream> 2 #include<cstdio> 3 #include<string> 4 #include<cstring> 5 #include<cmath> 6 #include<algorithm> 7 #define N 10000005 8 using namespace std; 9 int n; 10 int h[N],biuld[N]; 11 int max_h=-1;; 12 int ans=0; 13 int main(){ 14 scanf("%d",&n); 15 for(int i=1;i<=n;i++){ 16 scanf("%d",&h[i]); 17 max_h=max(h[i],max_h); 18 } 19 for(int i=1;i<=max_h;i++){ 20 int cnt=0; 21 memset(biuld,0,sizeof(n+1)); 22 for(int j=1;j<=n;j++){ 23 if(h[j]>=i){//假如还需要加高度 24 biuld[++cnt]=j;//存储第几个 25 //cout<<biuld[cnt]<<endl; 26 } 27 } 28 // cout<<endl; 29 ans++; 30 for(int i=1;i<=cnt-1;i++){//判断需要几次操作 31 if(biuld[i+1]-biuld[i]>=2){//假如不是相邻的 32 ans++; 33 } 34 } 35 } 36 cout<<ans; 37 38 return 0; 39 }
代码2(100’):
1 #include<iostream> 2 #include<cstdio> 3 using namespace std; 4 int n,ans=0; 5 int h[1000001]; 6 int main(){ 7 cin>>n; 8 h[0]=0; 9 for(int i=1;i<=n;i++){ 10 cin>>h[i]; 11 if(h[i]>h[i-1]){//假如后面的比前面的要小 12 ans+=h[i]-h[i-1]; 13 } 14 } 15 cout<<ans; 16 17 return 0; 18 }