标签:
题意:
输入 n,m,w, n个数,每次将三个连续的w个数+1,加m次,使得最终的序列最大,输出最大序列里的最小的数
二分+贪心(详见代码)
1 #include <iostream> 2 #include <algorithm> 3 #include <string.h> 4 using namespace std; 5 #define inf 0x3f3f3f3f 6 int a[100010],b[100010],memory[200020]; 7 int main() 8 { 9 int n,m,w,l=inf,r=-inf; 10 int i,j; 11 cin>>n>>m>>w; 12 for(i=0;i<n;i++) 13 { 14 cin>>a[i]; 15 l = min(l,a[i]); 16 r = max(r,a[i]); 17 } 18 r+=m; //所能达到的最高长度 19 while(l<=r)//注意等号 20 { 21 int tempm = m,x=0; 22 // 受前面浇花的影响,也应该得到的浇花天数,如第i朵浇了x天,w=3, 23 //那么第i+1,i+2也应该浇x天 24 int mid = (l+r)>>1; 25 for(i=0;i<n;i++) 26 b[i] = max(0,mid-a[i]); //用b保存长到mid高度是需要的天数 27 memset(memory,0,sizeof(memory)); //用memory存结束w长度的浇花 28 for(i=0;i<n;i++) 29 { 30 x+=memory[i]; 31 if((b[i]-x)>0) 32 { 33 b[i]-=x; 34 tempm-=b[i]; 35 if(tempm<0) break; 36 x+=b[i];//累计能从前面浇花得到的天数 37 memory[i+w] -= b[i];//长度活了w后将得到的浇花天数还回去 38 } 39 } 40 if(tempm>=0) l = mid+1; 41 else r = mid-1; 42 } 43 cout<<l-1<<endl; 44 return 0; 45 }
标签:
原文地址:http://www.cnblogs.com/yscc/p/4342995.html