National Pig kill | topic

#include<stdio.h>
#include<map>
#include<iostream>
#include<algorithm>
using namespace std;
const int maxn=15,maxm=2005;
int i,j,k,m,n,used,now,id,to;
int kind[maxn],cnt[maxn],pig[maxn],pre[maxn][maxm],suc[maxn][maxm],end[maxn],card[maxn][maxm],pile[maxn],lst[maxn],nxt[maxn],life[maxn],fig[maxn],wpn[maxn];
string s;
map<string,int>mp;
string MP[maxm];
inline void swp(int &a,int &b){
	a+=b,b=a-b,a-=b;
}
inline void init(){
	mp["P"]=1,mp["K"]=2,mp["D"]=3,mp["F"]=4,mp["N"]=5,mp["W"]=6,mp["J"]=7,mp["Z"]=8;
	MP[1]="P",MP[2]="K",MP[3]="D",MP[4]="F",MP[5]="N",MP[6]="W",MP[7]="J",MP[8]="Z";
}
inline int newcard(){
	return used==m? pile[m]:pile[++used];
}
inline void check(){
	if(pig[1]&&pig[3])
		return ;
	if(pig[1]==0)
		puts("FP");
	else puts("MP");
	for(int i=1;i<=n;i++){
		if(life[i]<=0){
			puts("DEAD");
			continue;
		}
		for(int j=suc[i][0];j;j=suc[i][j])
			cout<<MP[card[i][j]]<<" ";
		puts("");
	}
	exit(0);
}
inline void get(int x,int y){
	card[x][++cnt[x]]=y,pre[x][cnt[x]]=end[x],suc[x][end[x]]=cnt[x],end[x]=cnt[x];
}
inline void discard(int x,int y){
//	printf("%d use ",x);
//	cout<<MP[card[x][y]]<<endl;
	pre[x][suc[x][y]]=pre[x][y],suc[x][pre[x][y]]=suc[x][y];
	if(end[x]==y)
		end[x]=pre[x][y];
}
inline int have(int x,int y){
	for(int i=suc[x][0];i;i=suc[x][i])
		if(card[x][i]==y){
			discard(x,i);
			return 1;
		}
	return 0;
}
inline int rlt(int x,int y){
	if(fig[y]==0)
		return 0;
	if(fig[y]==4)
		return kind[x]==1? 2:0;
	if(kind[x]==1||kind[x]==2)
		return (fig[y]==1||fig[y]==2)? 1:2;	
	if(kind[x]==3)
		return (fig[y]==1||fig[y]==2)? 2:1;
	return 0;
}
inline void change(int x,int y,int w){
	fig[x]=w==0? kind[x]:(kind[y]==1? 4:fig[x]);
}
inline void attack(int x,int y){
//	printf("%d attack %d\n",x,y);
	life[y]--;
	if(life[y]==0){
		for(int i=suc[y][0];i;i=suc[y][i])
			if(card[y][i]==1){
				life[now]++,discard(y,i);
				return ;
			}
		lst[nxt[y]]=lst[y],nxt[lst[y]]=nxt[y];
		pig[kind[y]]--;
		check();
		if(kind[x]==1&&kind[y]==2)
			end[1]=suc[1][0]=wpn[1]=0;
		if(kind[y]==3)
			get(x,newcard()),get(x,newcard()),get(x,newcard());
	}
}
int cancel(int x,int y,int w){
	if(rlt(x,y)==w&&have(x,7)){
		change(x,y,0);
		if(cancel(x,y,3-w)==0)
			return 1;
	}
	for(int i=nxt[x];i!=x;i=nxt[i])
		if(rlt(i,y)==w&&have(i,7)){
			change(i,y,0);
			if(cancel(i,y,3-w)==0)
				return 1;
		}
	return 0;
}
void fight(int x,int y){
	if(cancel(x,y,1))
		return ;
	while(1){
		swp(x,y);
		if(have(x,2)==0||(kind[x]==2&&kind[y]==1)){
			attack(y,x);
			break;
		}
	}
}
void AOE(int x,int y,int w){
	if(cancel(x,y,1)||have(y,w))
		return ;
//	printf("%d AOE %d by %d\n",x,y,w);
	attack(x,y);
	change(x,y,1);
}
int main(){
	init();
	scanf("%d%d",&n,&m);
	for(i=1;i<=n;i++){
		cin>>s;
		kind[i]=(s=="MP"? 1:(s=="ZP"? 2:3));
		pig[kind[i]]++;
		for(j=1;j<=4;j++){
			cin>>s;
			get(i,mp[s]);
		}
		lst[i]=(i==1? n:i-1),nxt[i]=(i==n? 1:i+1);
		life[i]=4,fig[i]=0;
	}
	for(i=1;i<=m;i++){
		cin>>s;
		pile[i]=mp[s];
	}
	kind[1]=1;
	check();
	for(now=1;;now=nxt[now]){
		int use_K=0;
		get(now,newcard()),get(now,newcard());
		for(id=suc[now][0];id;id=suc[now][id]){
			if(card[now][id]==1){
				if(life[now]==4)
					continue;
//				printf("%d P\n",now);
				life[now]++;
				discard(now,id);
			}
			if(card[now][id]==2){
				if(use_K&&wpn[now]==0)
					continue;
				use_K++;
				int to=nxt[now];
				if(rlt(now,to)==2){
//					printf("%d K %d\n",now,to);
					discard(now,id);
					change(now,to,0);
					if(have(to,3)==0)
						attack(now,to);
				}
			}
			if(card[now][id]==4){
				if(kind[now]==3){
//					printf("%d F 1\n",now);
					discard(now,id);
					change(now,1,0);
					fight(now,1);
					id=0;
					continue;
				}
				for(to=nxt[now];to!=now;to=nxt[to])
					if(rlt(now,to)==2){
//						printf("%d F %d\n",now,to);
						discard(now,id);
						change(now,to,0);
						fight(now,to);
						id=0;
						break;
					}
				if(life[now]<=0)
					break;
			}
			if(card[now][id]==5||card[now][id]==6){
				discard(now,id);
				for(to=nxt[now];to!=now;to=nxt[to])
					AOE(now,to,card[now][id]);
				id=0;
			}
			if(card[now][id]==8){
//				printf("%d Z\n",now);
				discard(now,id);
				wpn[now]=1;
				id=0;
			}
		}
	}
	return 0;
}

  

Guess you like

Origin www.cnblogs.com/xiaoziyao/p/12089183.html
pig
pig