首先我们给蚯蚓从大到小排序。然后可以发现,每次切出来的蚯蚓中,长的那写按切的顺序形成非上升序列,短的那些也如此。那么我们维护3个单调队列即可(原始蚯蚓也算一个单调队列),每次找三个队列队首元素最大的那个,把这个蚯蚓切掉,然后分别插入两个单调队列中。最后也按照这样每次找出最大的,按要求把该输出的输出即可。由于最后有n+m只蚯蚓,所以这样的时间复杂度O(n+m)。
1 #include<set>
2 #include<map>
3 #include<list>
4 #include<queue>
5 #include<stack>
6 #include<string>
7 #include<cmath>
8 #include<ctime>
9 #include<vector>
10 #include<bitset>
11 #include<memory>
12 #include<utility>
13 #include<cstdio>
14 #include<sstream>
15 #include<iostream>
16 #include<cstdlib>
17 #include<cstring>
18 #include<algorithm>
19 using namespace std;
20
21 int n,m,q,u,v,g,del;
22 long long a[1000005],b[4][7000005],h[5],t[5];
23
24 int main(){
25 scanf("%d%d%d%d%d%d",&n,&m,&q,&u,&v,&g);
26 for(int i=1;i<=n;i++){
27 scanf("%lld",a+i);
28 }
29 sort(a+1,a+1+n);
30 for(int i=1;i<=n;i++){
31 b[1][n-i+1]=a[i];
32 }
33 h[1]=h[2]=h[3]=1;
34 t[1]=n;
35 t[2]=t[3]=0;
36 del=0;
37 for(int i=1;i<=m;i++){
38 long long ans=-1<<30,num=0;
39 for(int j=1;j<=3;j++){
40 if(h[j]<=t[j]&&b[j][h[j]]>ans){
41 ans=b[j][h[j]];
42 num=j;
43 }
44 }
45 if(i%g==0){
46 printf("%lld ",ans+del);
47 }
48 h[num]++;
49 b[2][++t[2]]=(long long)(ans+del)*u/v-del-q;
50 b[3][++t[3]]=ans+del-(long long)(ans+del)*u/v-del-q;
51 del+=q;
52 }
53 printf("\n");
54 for(int i=1;i<=m+n;i++){
55 long long ans=-1<<30,num=0;
56 for(int j=1;j<=3;j++){
57 if(h[j]<=t[j]&&b[j][h[j]]>ans){
58 ans=b[j][h[j]];
59 num=j;
60 }
61 }
62 if(i%g==0){
63 printf("%lld ",ans+del);
64 }
65 h[num]++;
66 }
67 return 0;
68 }