改了几个小时,80分吐了(10~13测试点)
查看原帖
改了几个小时,80分吐了(10~13测试点)
181433
abs_0楼主2021/1/2 11:08
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cmath>

using namespace std;

struct node{
	int dat,id;
	node(int dat0=0,int id0=0){
		dat=dat0;
		id=id0;
	}
};


int n,m,x0,h[100010],t;
int ga[100010],gb[100010],l[100010],r[100010],id1[100010];
int f[20][100010][2];
long long da[20][100010][2],db[20][100010][2];
node a[500010];
unsigned long long ans,ansa,ansb;
double ab;
long long la,lb;

void pre();
bool cmp(node x,node y);
int getg(int i,int j);
void dp();
int geth(int x,int y);
void calc(int s,int x);

int main(){
//	freopen("1081.in","r",stdin);
//	freopen("1081.out","w",stdout);
	scanf("%d",&n);
	for(int i=1;i<=n;i++){
		scanf("%d",&h[i]);
		a[i]=node(h[i],i);
	}
	t=log(n)/log(2);	
	pre();
	dp();
	scanf("%d",&x0);
	calc(1,x0);
	ans=1,ab=lb?(double)la/lb:2*1e9;
	for(int i=2;i<=n;i++){
		calc(i,x0);
		if(lb==0){
			if(ab==2*1e9&&h[ans]<h[i])
				ans=i;
			continue ;
		}
		if((double)la/lb<ab||((double)la/lb==ab&&h[ans]<h[i])){
			ab=(double)la/lb;
			ans=i;
		}
	}	
	printf("%d\n",ans);
	scanf("%d",&m);
	int x,s;
	for(int i=1;i<=m;i++){
		scanf("%d%d",&s,&x);
		calc(s,x);
		printf("%lld %lld\n",la,lb);
	}
	return 0;
}
void pre(){
	sort(a+1,a+n+1,cmp);
	for(int i=1;i<=n;i++){
		l[i]=i-1;
		r[i]=i+1;
		id1[a[i].id]=i;
	}
	r[n+1]=n+1;
	a[0].dat=-1e9-5,a[n+1].dat=1e9+5;
	for(int i=1;i<=n-2;i++){
		ga[i]=getg(i,2);
		gb[i]=getg(i,1);
		r[l[id1[i]]]=r[id1[i]];
		l[r[id1[i]]]=l[id1[i]];
	}
	gb[n-1]=n;
	ga[n-1]=ga[n]=gb[n]=0;
}
bool cmp(node x,node y){
	return x.dat<y.dat;
}
int getg(int i,int j){
	int x=l[id1[i]],y=r[id1[i]],k=id1[i];
	if(j==1){
		if(a[k].dat-a[x].dat>a[y].dat-a[k].dat)
			return a[y].id;
		return a[x].id; 
	}
	int x1=l[x],y1=r[y];
	if(a[k].dat-a[x].dat==a[y].dat-a[k].dat)
		return a[y].id;
	if(a[k].dat-a[x].dat<a[y].dat-a[k].dat){
		if(a[k].dat-a[x1].dat>a[y].dat-a[k].dat)
			return a[y].id;
		return a[x1].id;
	}
	if(a[k].dat-a[x].dat>a[y1].dat-a[k].dat)
		return a[y1].id;
	return a[x].id;
}
void dp(){
	for(int i=1;i<=n;i++){
		f[0][i][0]=ga[i];
		f[0][i][1]=gb[i];
	}
	for(int i=1;i<=n;i++){
		f[1][i][0]=f[0][f[0][i][0]][1];
		f[1][i][1]=f[0][f[0][i][1]][0];
	}
	for(int i=2;i<=t;i++)
		for(int j=1;j<=n;j++){
			f[i][j][0]=f[i-1][f[i-1][j][0]][0];
			f[i][j][1]=f[i-1][f[i-1][j][1]][1];
		}
	for(int i=1;i<=n;i++){
		da[0][i][0]=geth(i,f[0][i][0]);
		db[0][i][1]=geth(i,f[0][i][1]);
	}
	for(int i=1;i<=n;i++){
		da[1][i][0]=da[0][i][0];
		da[1][i][1]=da[0][f[0][i][1]][0];
		db[1][i][1]=db[0][i][1];
		db[1][i][0]=db[0][f[0][i][0]][1];
	}
	for(int i=2;i<=t;i++)
		for(int j=1;j<=n;j++){
			da[i][j][0]=da[i-1][j][0]+da[i-1][f[i-1][j][0]][0];
			da[i][j][1]=da[i-1][j][1]+da[i-1][f[i-1][j][1]][1];
			db[i][j][0]=db[i-1][j][0]+db[i-1][f[i-1][j][0]][0];
			db[i][j][1]=db[i-1][j][1]+db[i-1][f[i-1][j][1]][1];
		}	
}
int geth(int x,int y){
	return abs(h[x]-h[y]);
}
void calc(int s,int x){
	int p=s;
	la=lb=0;
	for(int i=t;i>=0;i--)
		if(la+lb+da[i][p][0]+db[i][p][0]<=x&&f[i][p][0])
			la+=da[i][p][0],lb+=db[i][p][0],p=f[i][p][0];
}
2021/1/2 11:08
加载中...