답안 #738335

# 제출 시각 아이디 문제 언어 결과 실행 시간 메모리
738335 2023-05-08T14:17:41 Z bobthebuilder 식물 비교 (IOI20_plants) C++17
17 / 100
1210 ms 110952 KB
#include "plants.h"
#include<bits/stdc++.h>
using namespace std;
#define sz(x) (int)x.size()
#define REP(i,n) for(int i=0;i<n;i++)
#define REP1(i,n) for(int i=1;i<=n;i++)
#define pb push_back
#define lowb(x) (x&(-x))
#define ALL(_x) _x.begin(),_x.end()
#define pii pair<int,int>
#define f first
#define s second
#define SORT_UNIQUE(x) sort(ALL(x)),x.erase(unique(ALL(x)),x.end())
#define ll long long
#define MNTO(x,y) x=min(x,y)
#define MXTO(x,y) x=max(x,y)
const int maxn=2e5+5;
const int INF=0x3f3f3f3f;
namespace {
int seg[4*maxn],pos[4*maxn];
int arr[maxn];
int lazy[4*maxn];
int ans[2*maxn];
int cur;
int k;
int n;
}
void pushdown(int idx,int l,int r){
	if(!lazy[idx]){
		return;
	}
	seg[idx]+=lazy[idx];
	if(l==r){
		lazy[idx]=0;
		return;
	}
	lazy[idx*2]+=lazy[idx];
	lazy[idx*2+1]+=lazy[idx];
	lazy[idx]=0;
}
void build(int idx,int l,int r){
	
	if(l==r){
		seg[idx]=arr[l];
		pos[idx]=l;
		return;
	}
	int mid=(l+r)/2;
	build(idx*2,l,mid),build(idx*2+1,mid+1,r);
	seg[idx]=min(seg[idx*2],seg[idx*2+1]);
	if(seg[idx]==seg[idx*2]) pos[idx]=pos[idx*2];
	else pos[idx]=pos[idx*2+1];
}
void upd(int idx,int l,int r,int ql,int qr,int x){
	if(ql>qr) return;
	pushdown(idx,l,r);
	if(r<ql or l>qr) return;
	if(ql<=l and r<=qr){
		lazy[idx]+=x;
		pushdown(idx,l,r);
		return;
	}
	int mid=(l+r)/2;
	upd(idx*2,l,mid,ql,qr,x);
	upd(idx*2+1,mid+1,r,ql,qr,x);
	seg[idx]=min(seg[idx*2],seg[idx*2+1]);
	if(seg[idx]==seg[idx*2]) pos[idx]=pos[idx*2];
	else pos[idx]=pos[idx*2+1];
}
pii query(int idx,int l,int r,int ql,int qr){
	if(ql>qr) return {INF,-1};
	pushdown(idx,l,r);
	if(r<ql or l>qr) return {INF,-1};
	if(ql<=l and r<=qr){
		return {seg[idx],pos[idx]};
	}
	int mid=(l+r)/2;
	return min(query(idx*2,l,mid,ql,qr),query(idx*2+1,mid+1,r,ql,qr));
}

void get(int z){
	//cout<<z<<'\n';
	pii mn;
	while(true){
		if(z-k<0){
			mn=min(query(1,0,n-1,0,z-1),query(1,0,n-1,n+(z-k),n-1));
		}
		else{
			mn=query(1,0,n-1,z-k,z-1);
		}
		if(mn.f==0){
			get(mn.s);
		}
		else{
			break;
		}
	}
	ans[z]=cur--;
	if(z-k<0){
		upd(1,0,n-1,0,z-1,-1);
		upd(1,0,n-1,n+(z-k),n-1,-1);
	}
	else{
		upd(1,0,n-1,z-k,z-1,-1);
	}
	upd(1,0,n-1,z,z,INF);
}
vector<vector<int>> nxti,nxtd;
void init(int K, std::vector<int> r) {
	k=K;
	--k;
	n=sz(r);
	REP(i,n){
		arr[i]=r[i];
	}
	cur=n;
	build(1,0,n-1);
	while(cur>0){
		int z=query(1,0,n-1,0,n-1).s;
		assert(query(1,0,n-1,0,n-1).f==0);
		get(z);
	}
	REP(i,n) ans[i+n]=ans[i];
	//REP(i,n) cout<<ans[i]<<' ';
	//cout<<'\n';
	set<pii> s;
	nxti.assign(2*n,vector<int>(20,-1));
	nxtd.assign(2*n,vector<int>(20,-1));
	for(int i=2*n-1;i>=0;i--){
		auto it=s.lower_bound({ans[i],i});
		nxti[i][0]=(it==s.end())?-1:(it->s);
		nxtd[i][0]=(it==s.begin())?-1:(prev(it)->s);
		//cout<<i<<' '<<nxti[i][0]<<' '<<nxtd[i][0]<<'\n';
		s.insert({ans[i],i});
		if(i+k<2*n){
			s.erase({ans[i+k],i+k});
		}
	}
	REP1(j,19){
		REP(i,2*n){
			if(nxti[i][j-1]!=-1){
				nxti[i][j]=nxti[nxti[i][j-1]][j-1];
			}
			else nxti[i][j]=-1;
			if(nxtd[i][j-1]!=-1){
				nxtd[i][j]=nxtd[nxtd[i][j-1]][j-1];
			}
			else nxtd[i][j]=-1;
		}
	}
}
bool ok(int x,int y,int t){
	auto &nxt=(t?nxtd:nxti);
	for(int j=19;j>=0;j--){
		if(nxt[x][j]!=-1 and y-nxt[x][j]>k){
			x=nxt[x][j];
		}
	}
	x=nxt[x][0];
	return (x!=-1 and y-x<=k and (t?ans[x]>ans[y]:ans[x]<ans[y]));
}
int compare_plants(int x, int y) {
	bool sam=(y-x<=k);
	if(ans[x]<ans[y]){
		sam|=ok(x,y,0);
		sam|=ok(y,x+n,1);
	}
	else{
		sam|=ok(x,y,1);
		sam|=ok(y,x+n,0);
	}
	if(!sam){
		return 0;
	}
	if(ans[x]>ans[y]) return 1;
	return -1;
} 
# 결과 실행 시간 메모리 Grader output
1 Correct 1 ms 340 KB Output is correct
2 Incorrect 0 ms 212 KB Output isn't correct
3 Halted 0 ms 0 KB -
# 결과 실행 시간 메모리 Grader output
1 Correct 0 ms 212 KB Output is correct
2 Incorrect 0 ms 212 KB Output isn't correct
3 Halted 0 ms 0 KB -
# 결과 실행 시간 메모리 Grader output
1 Correct 0 ms 212 KB Output is correct
2 Incorrect 0 ms 212 KB Output isn't correct
3 Halted 0 ms 0 KB -
# 결과 실행 시간 메모리 Grader output
1 Correct 0 ms 212 KB Output is correct
2 Correct 1 ms 340 KB Output is correct
3 Correct 132 ms 4104 KB Output is correct
4 Correct 894 ms 108160 KB Output is correct
5 Correct 990 ms 106864 KB Output is correct
6 Correct 1062 ms 106688 KB Output is correct
7 Correct 1184 ms 107140 KB Output is correct
8 Correct 1210 ms 110952 KB Output is correct
9 Correct 859 ms 106760 KB Output is correct
10 Correct 888 ms 106740 KB Output is correct
11 Correct 718 ms 106104 KB Output is correct
12 Correct 797 ms 106580 KB Output is correct
13 Correct 815 ms 109488 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 1 ms 212 KB Output is correct
2 Incorrect 1 ms 212 KB Output isn't correct
3 Halted 0 ms 0 KB -
# 결과 실행 시간 메모리 Grader output
1 Correct 1 ms 212 KB Output is correct
2 Incorrect 0 ms 212 KB Output isn't correct
3 Halted 0 ms 0 KB -
# 결과 실행 시간 메모리 Grader output
1 Correct 1 ms 340 KB Output is correct
2 Incorrect 0 ms 212 KB Output isn't correct
3 Halted 0 ms 0 KB -