ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

P1312 Mayan游戏 题解

2020-07-29 15:33:10  阅读:232  来源: 互联网

标签:register return int 题解 Mayan -- P1312 && bool


传送门

思路很简单, 模拟, 搜索

注意向左交换和向右交换其实是等价的, 所以不用枚举向左交换(因为优先向右交换)

但是如果当前枚举的块左边为空, 不存在过从左边向右交换的情况, 所以这种情况要额外判断, 多一个向左交换的搜索子树

代码

#include <cstdio>
#include <cstring>
int n;
struct M {
	int a[8][6];
	inline bool down(int x, int y) {
		int b[8];
		for (register int i = 1; i <= 7; i++) b[i] = a[i][y];
		for (register int i = x; i >= 1; i--)
			if (b[i]) {
				for (register int j = i; j >= 1; j--)
					a[x + (j - i)][y] = b[j], a[j][y] = 0;
				return 1;
			}
		return 0;
	}
	inline bool fall() {
		bool flag = 0;
		for (register int i = 1; i <= 5; i++)
			for (register int j = 7; j >= 2; j--)
				if (!a[j][i] && !(flag |= down(j, i))) break;
		return flag;
	}
	inline void del() {
		int b[8][6];
		memcpy(b, a, sizeof(a));
		for (register int i = 1; i <= 7; i++)
			for (register int j = 1; j <= 5; j++) 
				if (a[i][j]) {
					if(j >= 2 && j <= 4 && a[i][j - 1] == a[i][j] && a[i][j + 1] == a[i][j])
						b[i][j] = b[i][j - 1] = b[i][j + 1] = 0;
					if(i >= 1 && i <= 6 && a[i - 1][j] == a[i][j] && a[i + 1][j] == a[i][j])
						b[i][j] = b[i - 1][j] = b[i + 1][j] = 0;
				}
		memcpy(a, b, sizeof(b));
	}
	inline bool empty() {
		for (register int i = 1; i <= 7; i++)
			for (register int j = 1; j <= 5; j++)
				if (a[i][j]) return 0;
		return 1;
	}
	inline void update() {
		do del(); while(fall());
	}
	M drag(int x, int y, int g) {
		M nxt = *this;
		nxt[x][y] ^= nxt[x][y + g];
		nxt[x][y + g] ^= nxt[x][y];
		nxt[x][y] ^= nxt[x][y + g];
		nxt.update();
		return nxt;
	}
	void print() {
		puts("---------");
		for (int i = 1; i <= 7; i++) {
			for (int j = 1; j <= 5; j++) printf("%d ", a[i][j]);
			puts("");
		}
		puts("---------");
	}
	bool operator==(M b) {
		for (register int i = 1; i <= 7; i++)
			for (register int j = 1; j <= 5; j++)
				if (a[i][j] != b[i][j]) return 0;
		return 1;
	}
	int* operator[](int i) { return a[i]; }
	M () { memset(a, 0, sizeof(a)); }
	M (int v) { memset(a, v, sizeof(a)); }
};
int path[6][3], pi;
bool dfs(M a, int step) {
	if (step >= n && a.empty()) return 1;
	else if (step >= n) return 0;
	else if (a.empty()) return 0;
	for (int j = 1; j <= 5; j++)
		for (int i = 7; i >= 1; i--)
			if (a[i][j]) {
				if (j <= 4 && a[i][j] != a[i][j + 1] && dfs(a.drag(i, j, 1), step + 1))
					return path[++pi][0] = i, path[pi][1] = j, path[pi][2] = 1;
				if (j >= 2 && !a[i][j - 1] && dfs(a.drag(i, j, -1), step + 1))
					return path[++pi][0] = i, path[pi][1] = j, path[pi][2] = -1;
			}
	return 0;
}
int main() {
	scanf("%d", &n);
	M a;
	for (int i = 1, t, ti = 0; ti = 0, i <= 5; i++)
		while(scanf("%d", &t), t) a[8 - (++ti)][i] = t;	
	if (dfs(a, 0)) { 
		for (int i = pi; i >= 1; i--)
			printf("%d %d %d\n", path[i][1] - 1, 7 - path[i][0], path[i][2]);
	}
	else puts("-1");
	return 0;
}

魔改版(大雾)

#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <ctime>
int n;
struct M {
	int a[8][6];
	inline bool down(int x, int y) {
		int b[8];
		for (register int i = 1; i <= 7; i++) b[i] = a[i][y];
		for (register int i = x; i >= 1; i--)
			if (b[i]) {
				for (register int j = i; j >= 1; j--)
					a[x + (j - i)][y] = b[j], a[j][y] = 0;
				return 1;
			}
		return 0;
	}
	inline bool fall() {
		bool flag = 0;
		for (register int i = 1; i <= 5; i++)
			for (register int j = 7; j >= 2; j--)
				if (!a[j][i] && !(flag |= down(j, i))) break;
		return flag;
	}
	inline void del() {
		int b[8][6];
		memcpy(b, a, sizeof(a));
		for (register int i = 1; i <= 7; i++)
			for (register int j = 1; j <= 5; j++) 
				if (a[i][j]) {
					if(j >= 2 && j <= 4 && a[i][j - 1] == a[i][j] && a[i][j + 1] == a[i][j])
						b[i][j] = b[i][j - 1] = b[i][j + 1] = 0;
					if(i >= 1 && i <= 6 && a[i - 1][j] == a[i][j] && a[i + 1][j] == a[i][j])
						b[i][j] = b[i - 1][j] = b[i + 1][j] = 0;
				}
		memcpy(a, b, sizeof(b));
	}
	inline bool empty() {
		for (register int i = 1; i <= 7; i++)
			for (register int j = 1; j <= 5; j++)
				if (a[i][j]) return 0;
		return 1;
	}
	M update() {
		do del(); while(fall());
		return *this;
	}
	M drag(int x, int y, int g) {
		M nxt = *this;
		nxt[x][y] ^= nxt[x][y + g];
		nxt[x][y + g] ^= nxt[x][y];
		nxt[x][y] ^= nxt[x][y + g];
		nxt.update();
		return nxt;
	}
	M print() {
		puts("\033c");
		printf(" ");
		for (int i = 0; i <= 4; i++) printf("%2d", i);
		puts("");
		for (int i = 1; i <= 7; i++) {
			printf("%d", 7 - i);
			for (int j = 1; j <= 5; j++) printf("\033[3%d;7m  \033[0m", a[i][j]);
			puts("");
		}
		return *this;
	}
	bool isend() {
		int vis[10] = {0};
		for (int i = 1; i <= 7; i++)
			for (int j = 1; j <= 5; j++)
				vis[a[i][j]]++;
		for (int i = 1; i <= 10; i++)
			if (vis[i] >= 3) return 0;
		return 1;
	}
	bool operator==(M b) {
		for (register int i = 1; i <= 7; i++)
			for (register int j = 1; j <= 5; j++)
				if (a[i][j] != b[i][j]) return 0;
		return 1;
	}
	int* operator[](int i) { return a[i]; }
	M () { memset(a, 0, sizeof(a)); }
	M (int v) { memset(a, v, sizeof(a)); }
};
int main() {
	srand(time(0));
	M a(0);
	for (int i = 1; i <= 7; i++)
		for (int j = 1; j <= 7; j++)
			a[i][j] = rand() % 4;
	a.update().print();
	if (a.isend()) return printf("0 step\n"), 0;
	int step = 0;
	while(1) {
		int x, y, g;
		a.print();
		scanf("%d%d%d", &x, &y, &g);
		if (x >= 1 && x <= 7 && y >= 1 && y <= 5 && (g == -1 || g == 1)) {
			a = a.drag(7 - y, x + 1, g).print();
			step++;
		}
		if (a.isend()) break;
	}
	printf("%d%s\n", step, step <= 1 ? "" : "s");
	return 0;
}

标签:register,return,int,题解,Mayan,--,P1312,&&,bool
来源: https://www.cnblogs.com/youxam/p/p1312.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有