列表

详情


NC13225. 围棋

描述

围棋是起源于中国有悠久历史的策略性棋类游戏。它的规则如下:
1. 棋盘19*19。
2. 棋子分黑白两色,双方各执一色。
3. 下法:每次黑或白着一子于棋盘的空点上。棋子下定后,不再向其他点移动。
4. 棋子的气:一个棋子在棋盘上,与它相邻的空点是这个棋子的“气”(这里相邻是指两个点有公共边)。 相邻的点上如果有同色棋子存在,这些棋子就相互连接成一个不可分割的整体,气合并计算。
相邻的点上如果有异色棋子存在,此处的气便不存在。
如果棋子所在的连通块失去所有的气,即为无气之子,不能在棋盘上存在。
5. 提子:把无气之子清理出棋盘的手段叫“提子”。提子有二种:
1) 着子后,对方棋子无气,应立即提取对方无气之子。
2) 着子后,双方棋子都呈无气状态,应立即提取对方无气之子。
6. 禁着点:棋盘上的任何一空点,如果某方在此下子,会使该子立即呈无气状态,同时又不能提取对方的棋子,这个点叫做“禁着点”,该方不能在此下子。
7. 禁止全局同形:无论哪一方,在成功进行了着子、提子操作后,棋盘局面不能和任何之前的局面相同。

你要做的是:输入一些操作,从空棋盘开始模拟这些操作。
对于每一步,若结果不正确,则输出对应的miss并且忽略这个操作,并在最后输出棋盘的局面。

输入描述

第一行,测试数据组数≤100
第二行,每组测试数据,执行的步数 n ≤ 2000
然后 n 行
B x y
W x y
(1 ≤ x ≤ 19,1 ≤ y ≤ 19) 其中,二元组 x,y 表示围棋棋盘上第 x 行第 y 列对应的点。 输入数据保证是黑白轮流下的。

输出描述

多行 对于miss的情况,输出是哪一种错误格式,其中: miss 1 表示下的位置已经有棋了 miss 2 表示违反规则6 miss 3 表示违反规则7 对于正常的操作,不用输出。 最后输出最终盘面。“B表示黑子,W表示白子,如果是空点的话,就输出'.'字符。”

示例1

输入:

1
12
B 1 3
W 1 2
B 2 4
W 2 1
B 1 1
W 2 3
B 3 3
W 3 2
B 1 1
W 2 3
B 2 2
W 2 3

对应的棋形是这样的:
<img src="https://uploadfiles.nowcoder.com/images/20170607/906271_1496803043049_ACDF8ED8821F13905E5C0A0E247B8C01" alt="" style="height:auto;width:138.6px;" />

输出:

miss 2
miss 2
miss 1
miss 3
.WB................
WB.B...............
.WB................
...................
...................
...................
...................
...................
...................
...................
...................
...................
...................
...................
...................
...................
...................
...................
...................

原站题解

上次编辑到这里,代码来自缓存 点击恢复默认模板

C++(g++ 7.5.0) 解法, 执行用时: 573ms, 内存消耗: 1592K, 提交时间: 2022-10-28 19:21:03

#include<bits/stdc++.h>
using namespace std;
char yy[21][21],nxt[21][21];
int dis[4][2]={{0,1},{0,-1},{1,0},{-1,0}},vis[21][21];
set<int>st;
void lint(){
	for(int i=1;i<=19;i++)for(int j=1;j<=19;j++)yy[i][j]=nxt[i][j]='.';
	st.clear();
}
void back_(){
	for(int i=1;i<=19;i++)for(int j=1;j<=19;j++)yy[i][j]=nxt[i][j];
}
void copy_(){
	for(int i=1;i<=19;i++)for(int j=1;j<=19;j++)nxt[i][j]=yy[i][j];
}
bool search(int x,int y,char ch){
	char ch2 = ch=='B'?'W':'B';
	bool have_air=0;
	if(yy[x][y]=='.')return true;
	if(yy[x][y]!=ch)return false;
	vis[x][y]=1;
	for(int i=0;i<4;i++){
		int ax=x+dis[i][0],ay=y+dis[i][1];
		if(!vis[ax][ay])have_air|=search(ax,ay,ch);
	}
	return have_air;
}
void pick(int x,int y,int ch2){
	yy[x][y]='.';
	for(int i=0;i<4;i++){
		int dx=x+dis[i][0];
		int dy=y+dis[i][1];
		if(yy[dx][dy]==ch2)pick(dx,dy,ch2);
	}
}
bool same(){
	int has=0;
	for(int i=1;i<=19;i++)for(int j=1;j<=19;j++)has=has*91+yy[i][j];
	if(st.find(has) == st.end()){
		st.insert(has);
		return false;
	}else return true;
}
void yu(){
	char a,b;
	int x,y;
	cin>>a>>x>>y;
	b = a=='B'?'W':'B';
	memset(vis,0,sizeof(vis));
	if(yy[x][y]!='.')cout<<"miss 1"<<endl;
	else{
		yy[x][y]=a;
		vis[x][y]=1;
		bool have_air=search(x,y,a);
		for(int i=0;i<4;i++){
			int cx=x+dis[i][0];
			int cy=y+dis[i][1];
			if(!vis[cx][cy]&&yy[cx][cy]==b&&!search(cx,cy,b)){
				have_air=true;
				pick(cx,cy,b);
			}
		}
		if(have_air){
			if(!same()){
				copy_();
			}else{
				cout<<"miss 3"<<endl;
				back_();
			}
		}else{
			cout<<"miss 2"<<endl;
			back_();
		}
	}
}
int main(){
	int n,t;
	cin>>t;
	while(t--){
		lint();
		cin>>n;
		for(int i=1;i<=n;i++)yu();
		for(int i=1;i<=19;i++){
			for(int j=1;j<=19;j++)cout<<nxt[i][j];
			cout<<endl;
		}
	}
	return 0;
}

上一题