Alice is so popular that she can receive many flowers everyday. She has N vases numbered from 0 to N-1. When she receive some flowers, she will try to put them in the vases, one flower in one vase. She randomly choose the vase A and try to put a flower in the vase. If the there is no flower in the vase, she will put a flower in it, otherwise she skip this vase. And then she will try put in the vase A+1, A+2, ..., N-1, until there is no flower left or she has tried the vase N-1. The left flowers will be discarded. Of course, sometimes she will clean the vases. Because there are too many vases, she randomly choose to clean the vases numbered from A to B(A <= B). The flowers in the cleaned vases will be discarded.
题意:有 0~n-1 共 n 个花瓶,一个花瓶可以插一束花,现在有两个操作,一个是从 A 号花瓶开始插 k 束花,若花瓶有花就顺延到下一个花瓶,直到插完 k 束花或插完 n-1 号花瓶,问她插的第一个和最后一个花瓶编号。第二个操作是清空一段区间的花,问共丢掉多少花。
线段树保存区间空瓶数、首个空瓶和末个空瓶。树上二分查找 k 个空瓶,并更新最大最小空瓶位置。区间清除。
1 #include<stdio.h>
2 #include<string.h>
3 const int maxm=50006;
4 const int INF=0x3f3f3f3f;
5
6 int st[maxm<<2],ma[maxm<<2],mi[maxm<<2];
7 int ch[maxm<<2];
8 int maxx,minn,k;
9
10 inline int max(int a,int b){return a>b?a:b;}
11 inline int min(int a,int b){return a<b?a:b;}
12
13 void build(int o,int l,int r){
14 ma[o]=r;
15 mi[o]=l;
16 st[o]=r-l+1;
17 ch[o]=0;
18 if(l==r)return;
19 int m=l+((r-l)>>1);
20 build(o<<1,l,m);
21 build(o<<1|1,m+1,r);
22 }
23
24 void pushdown(int o,int l,int r){
25 if(ch[o]==1){
26 ch[o<<1]=ch[o<<1|1]=1;
27 int m=l+((r-l)>>1);
28 st[o<<1]=st[o<<1|1]=0;
29 ma[o<<1]=ma[o<<1|1]=-1;
30 mi[o<<1]=mi[o<<1|1]=INF;
31 ch[o]=0;
32 }
33 else if(ch[o]==2){
34 ch[o<<1]=ch[o<<1|1]=2;
35 int m=l+((r-l)>>1);
36 st[o<<1]=m-l+1;
37 st[o<<1|1]=r-m;
38 ma[o<<1]=m;
39 ma[o<<1|1]=r;
40 mi[o<<1]=l;
41 mi[o<<1|1]=m+1;
42 ch[o]=0;
43 }
44 }
45
46 void update1(int o,int l,int r,int ql,int qr){
47 if(ql<=l&&qr>=r){
48 if(k>=st[o]){
49 k-=st[o];
50 maxx=max(maxx,ma[o]);
51 minn=min(minn,mi[o]);
52 ma[o]=-1;
53 mi[o]=INF;
54 st[o]=0;
55 ch[o]=1;
56 return;
57 }
58 else if(l==r)return;
59 }
60 pushdown(o,l,r);
61 int m=l+((r-l)>>1);
62 if(ql<=m&&k)update1(o<<1,l,m,ql,qr);
63 if(qr>=m+1&&k)update1(o<<1|1,m+1,r,ql,qr);
64 ma[o]=max(ma[o<<1],ma[o<<1|1]);
65 mi[o]=min(mi[o<<1],mi[o<<1|1]);
66 st[o]=st[o<<1]+st[o<<1|1];
67 }
68
69 int update2(int o,int l,int r,int ql,int qr){
70 if(ql<=l&&qr>=r){
71 int ans=r-l+1-st[o];
72 st[o]=r-l+1;
73 ma[o]=r;
74 mi[o]=l;
75 ch[o]=2;
76 return ans;
77 }
78 pushdown(o,l,r);
79 int m=l+((r-l)>>1);
80 int ans=0;
81 if(ql<=m)ans+=update2(o<<1,l,m,ql,qr);
82 if(qr>=m+1)ans+=update2(o<<1|1,m+1,r,ql,qr);
83 ma[o]=max(ma[o<<1],ma[o<<1|1]);
84 mi[o]=min(mi[o<<1],mi[o<<1|1]);
85 st[o]=st[o<<1]+st[o<<1|1];
86 return ans;
87 }
88
89 int main(){
90 int T;
91 scanf("%d",&T);
92 while(T--){
93 int n,m;
94 scanf("%d%d",&n,&m);
95 build(1,0,n-1);
96 for(int i=1;i<=m;++i){
97 int t;
98 scanf("%d",&t);
99 if(t==1){
100 int a;
101 scanf("%d%d",&a,&k);
102 maxx=-1;
103 minn=INF;
104 update1(1,0,n-1,a,n-1);
105 if(maxx==-1&&minn==INF)printf("Can not put any one.
");
106 else printf("%d %d
",minn,maxx);
107 }
108 else if(t==2){
109 int a,b;
110 scanf("%d%d",&a,&b);
111 printf("%d
",update2(1,0,n-1,a,b));
112 }
113 }
114 printf("
");
115 }
116 return 0;
117 }