1496. 页

Description

战神阿瑞斯听说2008年在中华大地上,将举行一届规模盛大的奥林匹克运动会,心中顿觉异常兴奋,他想让天马在广阔的天空上,举行一场精彩的天马队列变换表演。首先,战神安排n头高度不同的天马,排成一列。然后重复下面的变换:让中间的天马出列,然后该匹天马可以排在对首,也可以排在队尾,这样称为一次变换,直到出现这一列天马按从低到高的顺序排列为止。那么从初始状态到目标状态最少需要多少次变换呢?你能给战神阿瑞斯参谋参谋吗?

Input

输入文件horse.in中有两行,第一行只有一个整数n,表示天马数。
第二行有n个正整数,分别表示n匹天马的高度,每两个数字中间用一个空格分隔。

Output

输出文件horse.out只有一行,该行只有一个正整数,表示从初始状态到目标状态最少需要的变换次数。如果无论如何变换都不能得到从低到高的排列,则输出已行“No Answer”(不包括引号)。

Sample Input

3
179   173  175

Sample Output

2

Data Constraint

Hint

【数据限制】
100%的数据:n只取3、5、7、9四个数字中的一个,且天马的高度为160-190之间的整数。

Solution

对于n=3,发现答案实际上等于逆序对数。

对于n=5or7,可以双向bfs,用标记记录状态。

对于n=9,则用哈希数组(玄学)记录。

注意双向bfs的时候要取两个队列中头指针步数较小的进行扩展,否则答案会错。

Code1(70pts)

#include<cstdio> 
#include<cstring>
#include<algorithm>
#define I int
#define F(i,a,b) for(I i=a;i<=b;i++)
#define Fd(i,a,b) for(I i=a;i>=b;i--)
#define N 15
using namespace std;
I n,m,x,y,a1,a2,a3,ans=-1,a[N],cnt,p[10][2],l,r,ll,rr,S,T,f[3200000],g[3200000],b[3200000],bz[3200000];
struct node{I v,id;}s[N];
I cmp(node x,node y){return x.v<y.v;}
I main(){
	freopen("page.in","r",stdin);
	freopen("page.out","w",stdout);
	scanf("%d",&n);
	F(i,1,n) scanf("%d",&a[i]);
	if(n==3) printf("%d\n",(a[1]>a[2])+(a[1]>a[3])+(a[2]>a[3]));
	else if(n==5||n==7){
		p[1][0]=p[1][1]=1;
		F(i,2,8){p[i][0]=p[i-1][0]*6,p[i][1]=p[i-1][1]*8;}
		
		F(i,1,n) s[i]=node{a[i],i};
		sort(s+1,s+1+n,cmp);
		F(i,1,n) a[s[i].id]=i;
		S=T=0;
		F(i,1,n){
			S+=a[i]*p[i][n/7];
			T+=i*p[i][n/7];
		}
		memset(b,255,sizeof b);
		memset(bz,255,sizeof bz);
		l=r=ll=rr=0;
		b[f[++r]=S]=bz[g[++rr]=T]=0;
		while(l<r||ll<rr){
			if(l<r){
				x=f[++l];
				if(bz[x]>=0){ans=bz[x]+b[x];break;}
				
				a1=x%p[n/2+1][n/7],a2=(x%p[n/2+2][n/7])/p[n/2+1][n/7],a3=x/p[n/2+2][n/7];
				
				y=a1+a3*p[n/2+1][n/7]+a2*p[n][n/7];
				if(bz[y]>=0){ans=bz[y]+b[x]+1;break;}
				if(b[y]<0) b[f[++r]=y]=b[x]+1;
				
				y=a2+a1*p[2][n/7]+a3*p[n/2+2][n/7];
				if(bz[y]>=0){ans=bz[y]+b[x]+1;break;}
				if(b[y]<0) b[f[++r]=y]=b[x]+1;
			}
			if(ll<rr){
				x=g[++ll];
				if(b[x]>=0){ans=b[x]+bz[x];break;}
				
				a1=x%p[2][n/7],a2=(x%p[n/2+2][n/7])/p[2][n/7],a3=x/p[n/2+2][n/7];
				
				y=a2+a1*p[n/2+1][n/7]+a3*p[n/2+2][n/7];
				if(b[y]>=0){ans=b[y]+bz[x]+1;break;}
				if(bz[y]<0) bz[g[++rr]=y]=bz[x]+1;
				
				a1=x%p[n/2+1][n/7],a2=(x%p[n][n/7])/p[n/2+1][n/7],a3=x/p[n][n/7];
				
				y=a1+a3*p[n/2+1][n/7]+a2*p[n/2+2][n/7];
				if(b[y]>=0){ans=b[y]+bz[x]+1;break;}
				if(bz[y]<0) bz[g[++rr]=y]=bz[x]+1;
			}
		}
		if(ans==-1) printf("No Answer\n");
		else printf("%d\n",ans);
	}
	else{
		
	}
	return 0;
}

Code2(100pts)

对于不同的质数答案可能会不一样,母鸡......

#include<cstdio> 
#include<cstring>
#include<algorithm>
#include<cmath>
#define I int
#define F(i,a,b) for(I i=a;i<=b;i++)
#define Fd(i,a,b) for(I i=a;i>=b;i--)
#define N 15
#define M 372871
#define MM 372871
using namespace std;
I n,m,x,y,k,now,a1,a2,a3,ans=-1,a[N],p[13],l,r,ll,rr,S,T,f[1000000],g[1000000],s[372881],t[372881],b[372881],bz[372881];
struct node{I v,id;}o[N];
I cmp(node x,node y){return x.v<y.v;}
I pd(I x){
	F(j,2,x-1) if(x%j==0) return 0;	
	return 1;
}
I h(I x){
	k=x%M;
	while(b[k]&&b[k]!=x) if(++k==M) k=0;
	return k;
}
I ha(I x){
	k=x%MM;
	while(bz[k]&&bz[k]!=x) if(++k==MM) k=0;
	return k;
}
void ins(I type){
	if(type==1){
		m=ha(y);
		if(bz[m]==y) ans=t[m]+s[now]+1;
		m=h(y);
		if(!b[m]){f[++r]=y,s[m]=s[now]+1;}
	}
	else{
		m=h(y);
		if(b[m]==y) ans=s[m]+t[now]+1;
		m=ha(y);
		if(!bz[m]){g[++rr]=y,t[m]=t[now]+1;}
	}
}
I main(){
	freopen("page.in","r",stdin);
	freopen("page.out","w",stdout);
	/*F(i,502780,502880) if(pd(i)){
		printf("%d\n",i);
	}*/
	scanf("%d",&n);
	F(i,1,n) scanf("%d",&a[i]);
	if(n==3) printf("%d\n",(a[1]>a[2])+(a[1]>a[3])+(a[2]>a[3]));
	else{
		p[1]=p[1]=1;
		F(i,2,11) p[i]=p[i-1]*10;
		
		F(i,1,n) o[i]=node{a[i],i};
		sort(o+1,o+1+n,cmp);
		F(i,1,n) a[o[i].id]=i;
		S=T=0;
		F(i,1,n){
			S+=a[i]*p[i];
			T+=i*p[i];
		}
		l=r=ll=rr=0;
		m=h(f[++r]=S);b[m]=S;
		m=ha(g[++rr]=T);bz[m]=T;
		while(l<r||ll<rr){
			if(l<r&&s[h(f[l+1])]<=t[ha(g[ll+1])]){
				x=f[++l],now=h(x);
//				m=ha(x);
//				if(bz[m]==x){ans=t[m]+s[now];break;}

				a1=x%p[n/2+1],a2=(x%p[n/2+2])/p[n/2+1],a3=x/p[n/2+2];
				
				y=a1+a3*p[n/2+1]+a2*p[n];
				ins(1);
				if(ans>=0) break;
				y=a2+a1*p[2]+a3*p[n/2+2];
				ins(1);
				if(ans>=0) break;
			}
			if(ll<rr&&s[h(f[l+1])]>=t[ha(g[ll+1])]){
				x=g[++ll],now=ha(x);
//				m=h(x);
//				if(b[m]==x){ans=s[m]+t[now];break;}

				a1=x%p[2],a2=(x%p[n/2+2])/p[2],a3=x/p[n/2+2];
				
				y=a2+a1*p[n/2+1]+a3*p[n/2+2];
				ins(0);
				if(ans>=0) break;
				a1=x%p[n/2+1],a2=(x%p[n])/p[n/2+1],a3=x/p[n];
				
				y=a1+a3*p[n/2+1]+a2*p[n/2+2];
				ins(0);
				if(ans>=0) break;
			}
		}
		if(ans>=0&&ans<=30) printf("%d\n",ans);else printf("No Answer\n");
	}
	return 0;
} 

猜你喜欢

转载自blog.csdn.net/zsjzliziyang/article/details/107943381
今日推荐