标签:com getc ace printf 最大 class ++ color code
T1:排序后离散化。pos[i]记录第i块骨牌倒塌后会影响到的最远骨牌数,可以通过二分查找求得。
枚举放置骨牌能够使某一位置及其之后的骨牌全部倒塌时被毁坏的骨牌个数,对所有值取min即可。
Code:
1 #include<cstdio> 2 #include<cstring> 3 #include<algorithm> 4 #define inf 0x7fffffff 5 #define MN 100005 6 using namespace std; 7 inline int in(){ 8 int x=0;bool f=0; char c; 9 for (;(c=getchar())<‘0‘||c>‘9‘;f=c==‘-‘); 10 for (x=c-‘0‘;(c=getchar())>=‘0‘&&c<=‘9‘;x=(x<<3)+(x<<1)+c-‘0‘); 11 return f?-x:x; 12 } 13 struct st{ 14 int p,t; 15 }a[MN]; 16 int pos[MN],sum[MN],p2[MN],n,res=inf; 17 inline bool cmp(st a,st b){return a.p<b.p;} 18 int main() 19 { 20 n=in();a[0].p=-inf;pos[0]=sum[0]=0; 21 for (int i=1;i<=n;++i){a[i].p=in();a[i].t=a[i].p-in();} 22 sort(a+1,a+n+1,cmp); 23 for (int i=0;i<=n;++i) p2[i]=a[i].p; 24 for (int i=1;i<=n;++i) pos[i]=lower_bound(p2,p2+n+1,a[i].t)-p2; 25 for (int i=0;i<=n;++i){ 26 if (pos[i]>0) sum[i]=sum[pos[i]-1]+(i-pos[i]); 27 res=min(res,sum[i]+(n-i)); 28 }printf("%d",res);return 0; 29 }
T2:可被看作为点
与点
的斜率的绝对值。
可以发现,当选取三个点A(x1,y1),B(x2,y2),C(x3,y3)(x1<x2<x3)时,kAC一定小于或等于kAB或kBC.(kXY即为直线XY的斜率)
以此类推,选取多个点时的最大值只可能在相邻位置取到。
考虑将原数组差分后求绝对值,则一个数组的所有子数组的值之和即变为一个数组的所有子数组的最大值之和。
单调栈维护差分求绝对值后的值。注意不能取到l前的数。
Code:
1 #include<cstdio> 2 #include<cstring> 3 #include<algorithm> 4 #define ll long long 5 #define MN 100005 6 #define zxyer array 7 using namespace std; 8 inline int in(){ 9 int x=0;bool f=0; char c; 10 for (;(c=getchar())<‘0‘||c>‘9‘;f=c==‘-‘); 11 for (x=c-‘0‘;(c=getchar())>=‘0‘&&c<=‘9‘;x=(x<<3)+(x<<1)+c-‘0‘); 12 return f?-x:x; 13 } 14 int d[MN],st[MN],a[MN]; 15 int n,q,l,r,top; 16 ll sum[MN],ans; 17 int main() 18 { 19 n=in();q=in(); 20 for (int i=1;i<=n;++i) a[i]=in(),d[i]=abs(a[i]-a[i-1]); 21 for (int i=1;i<=q;++i){ 22 l=in();r=in();top=0; 23 st[top]=l;ans=0ll; 24 for (int j=l+1;j<=r;++j){ 25 while (top&&d[st[top]]<d[j]) --top;st[++top]=j; 26 sum[top]=sum[top-1]+1ll*(j-st[top-1])*d[j];ans+=sum[top]; 27 }printf("%lld\n",ans); 28 }return 0; 29 }
标签:com getc ace printf 最大 class ++ color code
原文地址:http://www.cnblogs.com/codingutopia/p/test170929.html