1.内存控制
2.敌兵布阵
4.广告牌
5.区间第k大数(模板题)
6.just a Hook
7.I Hate It
8.动态的最长递增子序列(区间更新题)
9.图灵树
10.覆盖的面积
14.买票问题
16.村庄问题
17.Hotel
19.矩形周长问题
23.区间第k大数问题
26.海报问题

1001

  1 /*
  2 
  3 内存控制
  4 4种操作:
  5 1.Reset 初始化
  6 2.New x 开辟长度为x的连续的空间,输出起始位置
  7 3.Free x 释放包含第x字节的块,整块都释放掉
  8 4.Get x  输出当前状态下,内存里第x块的起始位置
  9 
 10 思路:
 11 1.Reset 很简单,update(1,N,EMPTY,1);就可以了
 12         没有必要重新构树
 13 
 14 2.New  x 对于这个操作,和Hotel这道题是一样的。
 15         建立树的过程中保存了lmax,rmax,max。在查询的
 16         过程中有一些小的技巧。
 17 
 18 3.Free x 释放内存,开一个容器,维护这个容器的顺序。
 19         学到了很多容器的知识。海,以前没有学过容器
 20         还是学别人的。
 21 4.Get x 也是通过维护这个容器,来得到的。
 22 
 23 详细的见代码
 24 
 25 
 26 */
 27 
 28 #include<cstdio>
 29 #include<iostream>
 30 #include<cstdlib>
 31 #include<algorithm>
 32 #include<vector>
 33 #define EMPTY 2 //纯色  此题中代表  空的。
 34 #define HH 1 //混色  此题中代表 被占用了。
 35 using namespace std;
 36 
 37 
 38 
 39 struct node
 40 {
 41     int l;
 42     int r;
 43     int lmax,rmax,max;
 44     int len;
 45     int color;
 46 }f[50003*4];
 47 struct st
 48 {
 49     int begin;
 50     int end;
 51 };
 52 vector<st>tom;
 53 
 54 
 55 int hmax(int x,int y)
 56 {
 57     return x>y? x:y;
 58 }
 59 
 60 bool cmp1(st n1,st n2)
 61 {
 62     return n1.begin<n2.begin;
 63 }
 64 
 65 void build(int l,int r,int n) //建树。
 66 {
 67     int mid=(l+r)/2;
 68     f[n].l=l;
 69     f[n].r=r;
 70     f[n].color=0;
 71     f[n].len=f[n].r-f[n].l+1;
 72     f[n].lmax=f[n].rmax=f[n].max=f[n].len;
 73     if(l==r)
 74     return;
 75     build(l,mid,n*2);
 76     build(mid+1,r,n*2+1);
 77 }
 78 /*
 79 建设的过程也有一个小小的亮点,可以把
 80  f[n].lmax=f[n].rmax=f[n].max=f[n].len;
 81  用向上更新来写在build(mid+1,r,n*2+1)后,带上
 82 */
 83 
 84 void make_down(int n) //向下更新
 85 {
 86     if(f[n].color==EMPTY)
 87     {
 88         f[n*2].max=f[n*2].rmax=f[n*2].lmax=f[n*2].len;
 89         f[n*2+1].max=f[n*2+1].rmax=f[n*2+1].lmax=f[n*2+1].len;
 90     }
 91     else if(f[n].color==HH)
 92     {
 93         f[n*2].max=f[n*2].lmax=f[n*2].rmax=0;
 94         f[n*2+1].max=f[n*2+1].lmax=f[n*2+1].rmax=0;
 95     }
 96 
 97     f[n*2].color=f[n].color;
 98     f[n*2+1].color=f[n].color;
 99 
100     f[n].color=0;
101     f[n].lmax=f[n].rmax=f[n].max=0;
102 
103 }
104 
105 void make_up(node *father,node *l_child,node *r_child) //向上更新
106 {
107     father->lmax=(l_child->lmax==l_child->len)? l_child->lmax+r_child->lmax: l_child->lmax;
108     father->rmax=(r_child->rmax==r_child->len)? r_child->rmax+l_child->rmax: r_child->rmax;
109     father->max=hmax(hmax(father->lmax,father->rmax),
110                      hmax(l_child->max,
111                           hmax(r_child->max,l_child->rmax+r_child->lmax)));
112 }
113 //为什么这道题,有个小小的亮点,没有rnum ,lnum;
114 //仔细一想确实是不需要的..
115 
116 
117 
118 void update(int l,int r,int num,int n) //更新函数  区间[l,r],更新为num。
119 {
120     int mid=(f[n].l+f[n].r)/2;
121     if(f[n].l==l && f[n].r==r)
122     {
123         if(num==EMPTY)
124         {
125             f[n].lmax=f[n].rmax=f[n].max=f[n].len;
126         }
127         else f[n].lmax=f[n].rmax=f[n].max=0;
128         f[n].color=num;
129         return;
130     }
131 
132     if(f[n].color!=0)
133     make_down(n);
134     if(mid>=r)
135     update(l,r,num,n*2);
136     else if(mid<l)
137     update(l,r,num,n*2+1);
138     else
139     {
140         update(l,mid,num,n*2);
141         update(mid+1,r,num,n*2+1);
142     }
143     make_up(&f[n],&f[n*2],&f[n*2+1]);
144 }
145 
146 int query(int max,int n)
147 {
148     int cur=0;
149 
150     if(f[n].l==f[n].r)
151     return f[n].l;
152     if(f[n].color!=0) //刚开始,这个别丢了,居然Running time error。
153     make_down(n);
154 
155     if(f[n*2].max>=max)
156     cur=query(max,n*2);
157 
158     else if(f[n*2].rmax+f[n*2+1].lmax>=max)
159     return f[n*2].r-f[n*2].rmax+1;
160 
161     else if(f[n*2+1].max>=max)
162     cur=query(max,n*2+1);
163 
164     make_up(&f[n],&f[n*2],&f[n*2+1]);
165     return cur;
166 }
167 /*
168 刚开始    左子树,
169 然后是    左子树右边最大值+右子树左边最大值
170 最后才是  右子树
171 */
172 
173 void make_ini(int N,int M)
174 {
175     char a[10];
176     int x,l,r,tmp;
177     st hxl;
178     while(M--)
179     {
180         scanf("%s",a);
181         if(a[0]=='R')
182         {
183             update(1,N,EMPTY,1);
184             tom.clear();
185             printf("Reset Now\n");
186         }
187         if(a[0]=='N')
188         {
189             scanf("%d",&x);
190             if(f[1].max<x)
191             {
192                 printf("Reject New\n");
193             }
194             else
195             {
196                 l=query(x,1);
197                 r=l+x-1;
198                 hxl.begin=l;
199                 hxl.end=r;
200                 vector<st>::iterator it;
201                 it=upper_bound(tom.begin(),tom.end(),hxl,cmp1);//二分查找,前提是有序。
202                 tom.insert(it,hxl);
203                 printf("New at %d\n",l);
204                 update(l,r,HH,1);
205             }
206         }
207         else if(a[0]=='F')
208         {
209             scanf("%d",&x);
210             hxl.begin=x;
211             hxl.end=x;
212             vector<st>::iterator it;//容器的使用啊
213             it=upper_bound(tom.begin(),tom.end(),hxl,cmp1);
214 
215             tmp=it-tom.begin()-1;
216             if(tmp==-1 || tom[tmp].end<x)
217             printf("Reject Free\n");
218             else
219             {
220                 printf("Free from %d to %d\n",tom[tmp].begin,tom[tmp].end);
221                 update(tom[tmp].begin,tom[tmp].end,EMPTY,1);
222                 tom.erase(tom.begin()+tmp);
223             }
224         }
225         else if(a[0]=='G')
226         {
227             scanf("%d",&x);
228             if(x>tom.size())
229             printf("Reject Get\n");
230             else
231             printf("Get at %d\n",tom[x-1].begin);//容器的下标也是从0开始,所以要减1
232         }
233     }
234 }
235 
236 int main()
237 {
238     int N,M;
239     while(scanf("%d%d",&N,&M)>0)
240     {
241         tom.clear();//这个必须要的。
242         build(1,N,1);
243         make_ini(N,M);
244         printf("\n"); //!!
245     }
246     return 0;
247 }
View Code

相关文章:

  • 2022-12-23
  • 2021-07-18
  • 2022-12-23
  • 2022-12-23
  • 2021-05-21
猜你喜欢
  • 2021-09-17
  • 2022-12-23
  • 2021-08-26
  • 2022-01-10
  • 2021-09-30
相关资源
相似解决方案