【hihocoder1291 微软2016校园招聘4月在线笔试D】【逆序思维 并查集】Buiding in Sandbox 我的世界建方块合法性判定

本文主要是介绍【hihocoder1291 微软2016校园招聘4月在线笔试D】【逆序思维 并查集】Buiding in Sandbox 我的世界建方块合法性判定,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

Building in Sandbox

时间限制: 30000ms
单点时限: 3000ms
内存限制: 256MB

描述

Little Hi is playing a sandbox voxel game. In the game the whole world is constructed by massive 1x1x1 cubes. The edges of cubes are parallel to the coordinate axes and the coordinates (x, y, z) of the center of each cube are integers.


At the beginning there is nothing but plane ground in the world. The ground consists of all the cubes of z=0. Little Hi needs to build everything by placing cubes one by one following the rules:

1. The newly placed cube must be adjacent to the ground or a previously placed cube. Two cubes are adjacent if and only if they share a same face.

2. The newly placed cube must be accessible from outside which means by moving in 6 directions(up, down, left, right, forward, backward) there is a path from a very far place - say (1000, 1000, 1000) in this problem - to this cube without passing through ground or other cubes.

Given a sequence of cubes Little Hi wants to know if he can build the world by placing the cubes in such order.

输入

The first line contains the number of test cases T(1 <= T <= 10).

For each test case the first line is N the number of cubes in the sequence.

The following N lines each contain three integers x, y and z indicating the coordinates of a cube.


For 20% of the data, 1 <= N <= 1000, 1 <= x, y, z <= 10.

For 100% of the data, 1 <= N <= 100000, 1 <= x, y, z <= 100.

输出

For each testcase output "Yes" or "No" indicating if Little Hi can place the cubes in such order.

样例提示

In the first test case three cubes are placed on the ground. It's OK.

In the second test case (1, 3, 2) is neither on the ground nor adjacent to previous cubes. So it can't be placed.

In the last test case (2, 2, 1) can not be reached from outside. So it can't be placed.  

样例输入
3
3
1 1 1
1 2 1
1 3 1
3
1 1 1
1 2 1
1 3 2
17
1 1 1
1 2 1
1 3 1
2 3 1
3 3 1
3 2 1
3 1 1
2 1 1
2 1 2
1 1 2
1 2 2
1 3 2
2 3 2
3 3 2
3 2 2
2 2 2
2 2 1
样例输出
Yes
No
No

#include<stdio.h>
#include<iostream>
#include<string.h>
#include<string>
#include<ctype.h>
#include<math.h>
#include<set>
#include<map>
#include<vector>
#include<queue>
#include<bitset>
#include<algorithm>
#include<time.h>
using namespace std;
void fre() { freopen("c://test//input.in", "r", stdin); freopen("c://test//output.out", "w", stdout); }
#define MS(x,y) memset(x,y,sizeof(x))
#define MC(x,y) memcpy(x,y,sizeof(x))
#define MP(x,y) make_pair(x,y)
#define ls o<<1
#define rs o<<1|1
typedef long long LL;
typedef unsigned long long UL;
typedef unsigned int UI;
template <class T1, class T2>inline void gmax(T1 &a, T2 b) { if (b>a)a = b; }
template <class T1, class T2>inline void gmin(T1 &a, T2 b) { if (b<a)a = b; }
const int N = 105, M = 1e5+10, Z = 1e9 + 7, ms63 = 0x3f3f3f3f;
int casenum, casei;
bool e[N][N][N];
int n;
const int dz[6] = { -1,0,0,0,0,1 };
const int dx[6] = { 0,-1,0,0,1,0 };
const int dy[6] = { 0,0,-1,1,0,0 };
struct A
{int x, y, z;
}a[M];const int G = N * N * N;
int f[G];
int find(int x)
{return x == f[x] ? x : f[x] = find(f[x]);
}
const int V1 = 102 * 102;
const int V2 = 102;
bool merge(int x1, int y1, int z1, int x2, int y2, int z2)
{int o1 = x1*V1 + y1*V2 + z1;int o2 = x2*V1 + y2*V2 + z2;o1 = find(o1);o2 = find(o2);if (o1 != o2){f[o2] = o1;return 1;}else return 0;
}
bool solve()
{MS(e, 0);bool flag = 1;for (int i = 1; i <= n; ++i){scanf("%d%d%d", &a[i].x, &a[i].y, &a[i].z);if (!flag)continue;int x = a[i].x;int y = a[i].y;int z = a[i].z;if (e[x][y][z])flag = 0;e[x][y][z] = 1;if (z == 1)continue;int k; for (k = 0; k < 6; ++k){int xx = x + dx[k];int yy = y + dy[k];int zz = z + dz[k];if (e[xx][yy][zz])break;}if (k == 6)flag = 0;}if (!flag)return 0;for (int i = 0; i <= 101; ++i){for (int j = 0; j <= 101; ++j){for (int k = 1; k <= 101; ++k){int o = i*V2 + j*V1 + k;f[o] = o;}}}for (int i = 0; i <= 101; ++i){for (int j = 0; j <= 101; ++j){for (int k = 1; k <= 101; ++k) if(!e[i][j][k]){for (int d = 0; d < 6; ++d){int x = i + dx[d];int y = j + dy[d];int z = k + dz[d];if (x < 0 || x>101 || y < 0 || y>101 || z < 1 || z>101)continue;if (!e[x][y][z])merge(i, j, k, x, y, z);}}}}for (int i = n; i >= 1; --i){int x = a[i].x;int y = a[i].y;int z = a[i].z;e[x][y][z] = 0; for (int d = 0; d < 6; ++d){int xx = x + dx[d];int yy = y + dy[d];int zz = z + dz[d];if (xx < 0 || xx>101 || yy < 0 || yy>101 || zz < 1 || zz>101)continue;if (!e[xx][yy][zz])merge(x, y, z, xx, yy, zz);}if (merge(x, y, z, 101, 101, 101))return 0;}return 1;
}
int main()
{scanf("%d", &casenum);for (casei = 1; casei <= casenum; ++casei){scanf("%d", &n);puts(solve() ? "Yes" : "No");}return 0;
}
/*
【trick&&吐槽】
1,排序的时候千万不要有
if(lastkey!=b.lastkey)return lastkey<b.lastkey
而要直接写成return lastkey<b.lastkey,否则会出错
2,正难则反的"变删除为添加"的思想很常见也很重要
3,这题还要考虑z==0是不可到达的点集(虽然数据中没有这样的)【题意】
我的世界游戏
建筑可以在地上或者与其它建筑连起来,而且不能完全封闭要与外界极远点相通。
问你一个建筑书序是否合法【类型】
正难则反 并查集【分析】
地图很小,可以直接维护100*100*100的所有点
每个方格的放置也就意味着有些点之间的联系被打断。
"联系被打断"不是很好处理,我们正难则反,从最后状态开始向前倒序处理。
一个格子的撤回就变成了关系的连通性。
每个格子都要与极外点(如101*101*101)联通【时间复杂度&&优化】
O(1e6)*/


这篇关于【hihocoder1291 微软2016校园招聘4月在线笔试D】【逆序思维 并查集】Buiding in Sandbox 我的世界建方块合法性判定的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/610382

相关文章

MySQL使用binlog2sql工具实现在线恢复数据功能

《MySQL使用binlog2sql工具实现在线恢复数据功能》binlog2sql是大众点评开源的一款用于解析MySQLbinlog的工具,根据不同选项,可以得到原始SQL、回滚SQL等,下面我们就来... 目录背景目标步骤准备工作恢复数据结果验证结论背景生产数据库执行 SQL 脚本,一般会经过正规的审批

水位雨量在线监测系统概述及应用介绍

在当今社会,随着科技的飞速发展,各种智能监测系统已成为保障公共安全、促进资源管理和环境保护的重要工具。其中,水位雨量在线监测系统作为自然灾害预警、水资源管理及水利工程运行的关键技术,其重要性不言而喻。 一、水位雨量在线监测系统的基本原理 水位雨量在线监测系统主要由数据采集单元、数据传输网络、数据处理中心及用户终端四大部分构成,形成了一个完整的闭环系统。 数据采集单元:这是系统的“眼睛”,

电力系统中的A类在线监测装置—APView400

随着电力系统的日益复杂和人们对电能质量要求的提高,电能质量在线监测装置在电力系统中得到广泛应用。目前,市场上的在线监测装置主要分为A类和B类两种类型,A类和B类在线监测装置主要区别在于应用场景、技术参数、通讯协议和扩展性。选择时应根据实际需求和应用场景综合考虑,并定期维护和校准。电能质量在线监测装置是用于实时监测电力系统中的电能质量参数的设备。 APView400电能质量A类在线监测装置以其多核

揭秘世界上那些同时横跨两大洲的国家

我们在《世界人口过亿的一级行政区分布》盘点全球是那些人口过亿的一级行政区。 现在我们介绍五个横跨两州的国家,并整理七大洲和这些国家的KML矢量数据分析分享给大家,如果你需要这些数据,请在文末查看领取方式。 世界上横跨两大洲的国家 地球被分为七个大洲分别是亚洲、欧洲、北美洲、南美洲、非洲、大洋洲和南极洲。 七大洲示意图 其中,南极洲是无人居住的大陆,而其他六个大洲则孕育了众多国家和

poj 1182 并查集 食物链类

题意: 有n只动物,分别编号1....n。所有动物都属于A,B,C中的一种,已知A吃B,B吃C,C吃A。 按顺序给出下面两种共K条信息: 1. x 和 y 属于同一类。 2. x 吃 y 。 然而这些信息可能会出错,有可能有的信息和之前给出的信息矛盾,也有的信息可能给出的 x 和 y 不在n的范围内。 求k条信息中有多少条是不正确的。 解析: 对于每只动物,创建3个元素 i

poj 1127 线段相交的判定

题意: 有n根木棍,每根的端点坐标分别是 px, py, qx, qy。 判断每对木棍是否相连,当他们之间有公共点时,就认为他们相连。 并且通过相连的木棍相连的木棍也是相连的。 解析: 线段相交的判定。 首先,模板中的线段相交是不判端点的,所以要加一个端点在直线上的判定; 然后,端点在直线上的判定这个函数是不判定两个端点是同一个端点的情况的,所以要加是否端点相等的判断。 最后

JavaFX应用更新检测功能(在线自动更新方案)

JavaFX开发的桌面应用属于C端,一般来说需要版本检测和自动更新功能,这里记录一下一种版本检测和自动更新的方法。 1. 整体方案 JavaFX.应用版本检测、自动更新主要涉及一下步骤: 读取本地应用版本拉取远程版本并比较两个版本如果需要升级,那么拉取更新历史弹出升级控制窗口用户选择升级时,拉取升级包解压,重启应用用户选择忽略时,本地版本标志为忽略版本用户选择取消时,隐藏升级控制窗口 2.

Go Playground 在线编程环境

For all examples in this and the next chapter, we will use Go Playground. Go Playground represents a web service that can run programs written in Go. It can be opened in a web browser using the follow

POJ1988带权并查集

M u v 将u所在的堆移动到v所在的堆的上面 C u 求u的下面有多少块 带权并查集 import java.io.BufferedReader;import java.io.InputStream;import java.io.InputStreamReader;import java.io.PrintWriter;import java.math.BigInteger;i

POJ1703带权并查集

D: u v  u与v在不同的集合 A: u v  查询u与v的关系 1)压缩路径过程        fu->root   0  1  u-fu 0                 0  1   1                 1  0 2)合并过程 fu->fv      u->fu   0 1   v->fv 0            1 0 1            0