首页 > 其他分享 >UVA1030 题解

UVA1030 题解

时间:2023-09-10 14:12:50浏览次数:32  
标签:ch 删除 int 题解 UVA1030 char MAXN 立方体

思路分析

猜想

我们可以在题目中看出一下几个突破口:

  • 能“看穿”的位置所对应的单位立方体是一定不存在的。
  • 如果前视图的右上角的颜色 \(A\) 和顶视图的的右下角颜色 \(B\) 不同,那么对应的格子就一定不存在

在删除这个立方体后,我们还可以发现,挖去立方体的左侧和 \(B\) 左侧的颜色不同。这样,我们又能删除一个新的立方体,并且暴露出新的表面。当无法继续删除时,剩下的立方体就是质量最大的物体。

证明

为什么上面的猜想是正确的呢?

首先,不难证明第一次删除行为是必要的(即被删除的那个立方体不可能存在于任意可行解中),因为只要不删除这个立方体,对应的两个视图的“矛盾”将会一直存在;接下来,我们可以用数学归纳法来证明。我们假设算法的前 \(k\) 次删除时必要的,那么第 \(k+1\) 次删除是否也是必要的呢?由刚才的推理,我们不能通过继续删除立方体来消除矛盾,而由归纳假设,已经删除的立方体也不能回复,因此矛盾无法消除。

代码实现

#include <bits/stdc++.h>
#define rep(i, n) for (int i = 0; i < (n); i++)
using namespace std;
const int MAXN = 15;
int n;
char pos[MAXN][MAXN][MAXN], view[6][MAXN][MAXN];
char read() {
	char ch;
	while (true) {
		ch = getchar();
		if ((ch >= 'A' && ch <= 'Z') || ch == '.') return ch;
	}
}
void get(int op, int i, int j, int len, int &x, int &y, int &z) {
	switch (op) {
	case 0:
		x = len, y = j, z = i;
		break;
	case 1:
		x = n - 1 - j, y = len, z = i;
		break;
	case 2:
		x = n - 1 - len, y = n - 1 - j, z = i;
		break;
	case 3:
		x = j, y = n - 1 - len, z = i;
		break;
	case 4:
		x = n - 1 - i, y = j, z = len;
		break;
	case 5:
		x = i, y = j, z = n - 1 - len;
		break;
	}
}
int main() {
	while (scanf("%d", &n) == 1 && n) {
		rep(i, n) rep(k, 6) rep(j, n) view[k][i][j] = read();
		rep(i, n) rep(j, n) rep(k, n) pos[i][j][k] = '#';
		rep(k, 6) rep(i, n) rep(j, n)
			if (view[k][i][j] == '.')
				rep(p, n) {
				int x, y, z;
				get(k, i, j, p, x, y, z);
				pos[x][y][z] = '.';
			}
		while (true) {
			bool done = true;
			rep(k, 6) rep(i, n) rep(j, n)
				if (view[k][i][j] != '.') {
					rep(p, n) {
						int x, y, z;
						get(k, i, j, p, x, y, z);
						if (pos[x][y][z] == '.') continue;
						if (pos[x][y][z] == '#') {
							pos[x][y][z] = view[k][i][j];
							break;
						}
						if (pos[x][y][z] == view[k][i][j]) break;
						pos[x][y][z] = '.';
						done = false;
					}
				}
			if (done) break;
		}
		int ans = 0;
		rep(i, n) rep(j, n) rep(k, n)
			if (pos[i][j][k] != '.') ans++;
		printf("Maximum weight: %d gram(s)\n", ans);
	}
	return 0;
}

标签:ch,删除,int,题解,UVA1030,char,MAXN,立方体
From: https://www.cnblogs.com/IShallReturn/p/UVA1030-ti-jie.html

相关文章

  • CF431B 题解
    思路分析答题思路一道纯暴力题!因为我们发现数据最大是\(5\),而枚举全排列的时间复杂度为\(\mathcalO(n!)\),对于这种极小的数据范围是丝毫不用顾虑的,因为我们只需要执行\(120\)次。如何快速求出一个数组的全排列?我们可以使用dfs,一层一层获取这个数组的全排列。但是STL......
  • CF387B 题解
    思路分析因为最终要使得\(a,b\)相同,所以我们应该希望让相同的数字尽量相同。所以,我们需要先对\(a\)和\(b\)进行排序,这样子就可以使用双指针的方法来维护最终值了。我们定义\(l\)指针指向\(a_l\),\(r\)指针指向\(b_r\)。因为题目要求添加数字的次数最少,所以我们希望尽......
  • P9516 题解
    思路分析一道很有洛谷个性的模拟签到题。按照题意,我们只需读入\(a,b,c,d,e\),然后对其进行求和,然后依次根据洛谷咕值系统介绍进行判断即可。这样是不是太没有意思了?今天为大家带来一点干货作为福利!介绍:accumulate()函数!简略分析:这个函数可以求出一段区间内的数字之和。S......
  • P9517 题解
    思路分析我们只需要找到左边第一个大于\(0\)的位置\(l\)与右边第一个大于\(0\)的位置\(r\),输出\(r-l+1\)即可。但是很坑的一点是,如果\(∀i∈[1,n],a_i=0\),那么\(l\)和\(r\)会重合,代码会输出\(1\)!所以,我们需要定义一个\(flag\)来标记是否全部输入为\(0\)。代......
  • UVA11210 题解
    思路分析一道大模拟。一共只有\(34\)种牌,因此可以一次判断是否“听”这些牌。比如,为了判断是否“听”一万,只需要判断自己拿到这张一万后能否可以继续和牌。这样,问题就转化成了给定\(14\)张牌,判断是否可以和牌。为此,我们可以递归求解:首先将两张牌作为“将”,然后每次选\(3\)......
  • UVA1352 题解
    思路分析构造排列表立方体只有\(4\)个,暴力法是可行的。但是如果我们要暴力,首先得清楚一个立方体到底有几种不同的旋转方式。接下来,我们用“姿态”一词代替“旋转方法”。假设\(6\)个面的编号为\(1\sim6\),从中选择一个面作为“顶面”,“顶面”的对面为“底面”。然后我们在......
  • UVA11464 题解
    思路分析暴力枚举?我们可以枚举每个数字变或不变,最后判断整个矩阵是否满足条件。但是,这样做最多需要枚举\(2^{255}≈5\times10^{67}\)中情况,是一定会超时的。大眼观察注意到\(n\le15\),第一行只有不超过\(2^{15}=32768\)种可能,所以第一行的情况是可以枚举的。接下来,根据第......
  • 题解 SP4586 Texas Trip
    首先题目翻译是有问题的,求的不是矩形而是最小的正方形。Solution先考虑一下若正方形的边都只能平行于坐标轴怎么做:找到\(x,y\)方向的坐标最值,那么答案就是\(\max^2\{X_{\max}-X_{\min},Y_{\max}-Y_{\min}\}\)。接下来,若正方形可以是斜着的,我们只需把坐标轴旋转,然后同样找出......
  • 题解 P8389【[COI2021] Izvanzemaljci】
    (本题解的所有图片使用GeometryWidget进行绘制)(一)\(K=1\)情况\(K=1\)是平凡的。(二)\(K=2\)情况显然,对于平面内的两个不交正方形,存在至少一条平行于坐标轴的直线将它们划分到两侧。以直线平行于\(y\)轴为例。考虑按\(x\)轴正方向扫描线。先将点按照\(x\)坐标排序,维......
  • cnpm : 无法加载文件 \npm\cnpm.ps1,因为在此系统上禁止运行脚本。 问题解决
    很久没有弄前端VUE了。最近用到的vscode进行前端摸索。在用NPM的时候,发现有点慢,于是切换到了cnpm。在使用cnpm进行运行的时候报错了。“cnpm:无法加载文件C:\Users\Administrator\AppData\Roaming\npm\cnpm.ps1,因为在此系统上禁止运行脚本。有关详细信息,请参阅https:/go.mi......