整体二分……感谢zyf提供的入门题

  简单粗暴的做法:枚举每一个国家,二分他的$w_i$,然后计算……然而这样效率很低……

  整体二分就是:对所有的国家一起进行二分,$w_i$在mid之前的,进左边,否则进右边(是不是很像线段树呀~其实就是吧……

  其实感觉代码写起来也跟线段树有些相似?

  

  RE:我没有在结束的时候加if (L==R) return;这样的话,只靠开头的 if (!V[o].size()) return;当极限数据的时候,走到叶子再乘二的话,就超出4*N的范围了……就跑到外面去了……所以就RE了……

 1 /**************************************************************
 2     Problem: 2527
 3     User: Tunix
 4     Language: C++
 5     Result: Accepted
 6     Time:17700 ms
 7     Memory:56832 kb
 8 ****************************************************************/
 9  
10 //BZOJ 2527
11 #include<cstdio>
12 #include<vector>
13 #include<cstring>
14 #include<cstdlib>
15 #include<iostream>
16 #include<algorithm>
17 #define rep(i,n) for(int i=0;i<n;++i)
18 #define F(i,j,n) for(int i=j;i<=n;++i)
19 #define D(i,j,n) for(int i=j;i>=n;--i)
20 #define pb push_back
21 using namespace std;
22 typedef long long LL;
23 inline int getint(){
24     int r=1,v=0; char ch=getchar();
25     for(;!isdigit(ch);ch=getchar()) if (ch=='-') r=-1;
26     for(; isdigit(ch);ch=getchar()) v=v*10-'0'+ch;
27     return r*v;
28 }
29 const int N=3e5+10;
30 /*******************template********************/
31  
32  
33 int n,m,K,p[N],l[N],r[N],a[N],ans[N],tot;
34 vector<int>G[N],V[N<<2];
35 LL c[N];
36 void add(int x,LL v){
37     for(;x<=m;x+=x&(-x)) c[x]+=v;
38 }
39 LL sum(int x){
40     LL r=0;
41     for(;x;x-=x&(-x)) r+=c[x];
42     return r;
43 }
44 void solve(int o,int L,int R){
45     if (!V[o].size()) return;
46     int mid=(L+R)>>1;
47     F(i,L,mid){
48         if (l[i]>r[i]) add(1,a[i]);
49         add(l[i],a[i]); add(r[i]+1,-a[i]);
50     }
51     rep(i,V[o].size()){
52         int x=V[o][i]; LL y=0;
53         rep(j,G[x].size()){
54             y+=sum(G[x][j]);
55             if (y>=p[x]) break;
56         }
57         if (y>=p[x]){
58             if (L==R) ans[x]=L;
59             else V[o<<1].pb(x);
60         }else{
61             if (L==R) ans[x]=-1;
62             else{
63                 p[x]-=y;
64                 V[o<<1|1].pb(x);
65             }
66         }
67     }
68     F(i,L,mid){
69         if (l[i]>r[i]) add(1,-a[i]);
70         add(l[i],-a[i]); add(r[i]+1,a[i]);
71     }
72     if (L==R) return;
73     solve(o<<1,L,mid); solve(o<<1|1,mid+1,R);
74 }
75  
76 int main(){
77 #ifndef ONLINE_JUDGE
78     freopen("2527.in","r",stdin);
79     freopen("2527.out","w",stdout);
80 #endif
81     n=getint(); m=getint();
82     F(i,1,m){
83         int x=getint();
84         G[x].pb(i);
85     }
86     F(i,1,n) p[i]=getint();
87     K=getint();
88     F(i,1,K){
89         l[i]=getint(); r[i]=getint(); a[i]=getint();
90     }
91     F(i,1,n) V[1].pb(i);
92     solve(1,1,K);
93     F(i,1,n){
94         if (ans[i]!=-1) printf("%d\n",ans[i]);
95         else puts("NIE");
96     }
97     return 0;
98 }
99 
View Code

相关文章:

  • 2021-09-10
  • 2021-05-20
  • 2021-10-20
  • 2021-10-23
  • 2021-07-31
猜你喜欢
  • 2022-01-24
  • 2021-11-02
  • 2021-06-24
  • 2021-11-01
  • 2022-02-17
  • 2021-08-08
  • 2022-02-17
相关资源
相似解决方案