• ISIJ 2021 Training Contest 1


    链接:http://144.202.116.213/contest/4

    A

    略。

    B

    本来想尝试一下数位 dp 的非递归方法,结果写挂了,最后只好写的递归……

    解法显然,略。

    C

    首先可以发现,我们只要确定了 (A) 中的前两个元素,后面的元素也都确定了:设 (A_1=x,A_2=y),那么因为 (A) 是“和谐”的,所以只能这样填:({x,y,y-x,-x,-y,x-y,dots})

    于是 (mathrm{dis}(A,B)=|x-B_1|+|y-B_2|+|y-x-B_3|+|-x-B_4|+|-y-B_5|+|x-y-B_6|+dots)。将 (B_{6k+3},B_{6k+4},B_{6k+5}) 变成相反数,那么就只需要考虑 ({x,y,x-y}) 的影响了。

    考虑到 (x)(y) 中一定有至少一个会取 (B) 中的值。

    枚举 (x)(y) 一定要取 ({B_{3k+2},x-B_{3k+3}}) 这些数的中位数。这个减号不太好处理,可以仿照上文相反数的处理方法,将它变成加号。

    枚举 (y)(x) 一定要取 ({B_{3k+1},y+B_{3k+3}}) 这些数的中位数。

    以枚举 (y) 为例:维护两个指针 (p_1,p_2) 表示 (B_{3k+1}) 中最接近中位数的位置、(y+B_{3k+3}) 中最接近中位数的位置。可以发现 在 (y) 单调递增的同时,(p_1) 是单调不减的、(p_2) 是单调不增的。

    如果一个数 (x) 在数列 (S) 与它相等的范围是 ([l,r]),那么当且仅当 (lle lceildfrac{|S|}{2} ceilland rge lceildfrac{|S|}{2} ceil) 时,它是中位数

    两次枚举并维护。

    代码
    const int N=3e5+5;
    int n,m[4],p[4][N];ll b[4][N],ps[4][N];
    int L(int i,ll x){return lower_bound(b[i]+1,b[i]+m[i]+1,x)-b[i]-1;}
    int Le(int i,ll x){return upper_bound(b[i]+1,b[i]+m[i]+1,x)-b[i]-1;}
    int G(int i,ll x){return m[i]-Le(i,x);}
    int Ge(int i,ll x){return m[i]-L(i,x);}
    bool Valid1_(int i,int j,ll x,ll mid,int len){
    	int l=L(i,mid)+L(j,mid-x);
    	return l<(len+1)/2;
    }
    bool Valid2_(int i,int j,ll x,ll mid,int len){
    	int r=Le(i,mid)+Le(j,mid-x);
    	return r>=(len+1)/2;
    }
    ll Dist(int i,ll x,int l=-1){
    	if(l==-1) l=L(i,x);
    	return x*l-ps[i][l]+(ps[i][m[i]]-ps[i][l])-x*(m[i]-l);
    }
    int main(){
    	Read(n);
    	For(i,1,n){
    		int j=(i-1)%3+1;
    		scanf("%lld",&b[j][++m[j]]);p[j][m[j]]=i;
    		if(i%6==4||i%6==5||i%6==0) b[j][m[j]]*=-1;
    	}
    	For(j,1,3) sort(b[j]+1,b[j]+m[j]+1);
    	For(j,1,3) For(i,1,m[j]) ps[j][i]=ps[j][i-1]+b[j][i];
    	ll ans=Inf;
    	for(int i=1,mp1=1,mp2=m[3];i<=m[1];++i){
    		ll x=b[1][i];ll res=Dist(1,x);
    		while(mp1<=m[2]&&!Valid2_(2,3,x,b[2][mp1],m[2]+m[3])) ++mp1;
    		while(mp2>=1&&!Valid1_(2,3,x,x+b[3][mp2],m[2]+m[3])) --mp2;
    		if(mp1<=m[2]&&Valid1_(2,3,x,b[2][mp1],m[2]+m[3])){
    			res+=Dist(2,b[2][mp1])+Dist(3,b[2][mp1]-x);
    		}else if(mp2>=1&&Valid2_(2,3,x,x+b[3][mp2],m[2]+m[3])){
    			res+=Dist(2,x+b[3][mp2])+Dist(3,b[3][mp2]);
    		}else res=Inf;
    		chkmin(ans,res);
    	}
    	For(j,1,3) For(i,1,m[j]){
    		if(p[j][i]%6==3||p[j][i]%6==0) b[j][i]*=-1;
    	}
    	For(j,1,3) sort(b[j]+1,b[j]+m[j]+1);
    	memset(ps,0,sizeof ps);
    	For(j,1,3) For(i,1,m[j]) ps[j][i]=ps[j][i-1]+b[j][i];
    	for(int i=1,mp1=1,mp2=m[3];i<=m[2];++i){
    		ll y=b[2][i];ll res=Dist(2,y);
    		while(mp1<=m[1]&&!Valid2_(1,3,y,b[1][mp1],m[1]+m[3])) ++mp1;
    		while(mp2>=1&&!Valid1_(1,3,y,y+b[3][mp2],m[1]+m[3])) --mp2;
    		if(mp1<=m[1]&&Valid1_(1,3,y,b[1][mp1],m[1]+m[3])){
    			res+=Dist(1,b[1][mp1])+Dist(3,b[1][mp1]-y);
    		}else if(mp2>=1&&Valid2_(1,3,y,y+b[3][mp2],m[1]+m[3])){
    			res+=Dist(1,y+b[3][mp2])+Dist(3,b[3][mp2]);
    		}else res=Inf;
    		chkmin(ans,res);
    	}
    	printf("%lld
    ",ans);
    	return 0;
    }
    
    Written by Alan_Zhao
  • 相关阅读:
    CSS3的box-sizing属性
    html5 --基础笔记2
    html5--基础笔记
    CSS3--阴影,渐变,背景图片
    响应式布局--流式布局
    angular中的this指向问题
    angular中控制器之间的通讯方式
    angular中的$http配置和参数
    console
    h5表单验证的css和js方法
  • 原文地址:https://www.cnblogs.com/alan-zhao-2007/p/isij-training-contest-1.html
Copyright © 2020-2023  润新知