hihoCoder #1291 : Building in Sandbox 逆向处理+并查集维护
/**
题目:#1291 : Building in Sandbox
链接:https://hihocoder.com/problemset/problem/1291
题意:就是一个三维的空间里,按照顺序放n个木块,每个木块满足两种条件。
1,和地面相邻或者和以前放过的木块有一个相邻的面。
2,不在封闭空间内。即可从无限远到达该木块。 判断该种放木块顺序是否合法。 思路:https://www.zhihu.com/question/42406890 逆向处理,并查集维护那些可以从无限远到达的位置称为自由块。 逆向处理的木块,当前木块如果和自由块相邻且和其他不是自由块的木块相邻或者地面相邻,那么当前木块合法。
将它变成自由块。然后更新和它相邻的那些不是自由块也不是木块的位置变成自由块。(相当于打开了一个缺口,水流进去了。) */ #include<iostream>
#include<cstdio>
#include<cstring>
#include<bitset>
#include<algorithm>
#include<queue>
using namespace std;
typedef unsigned int ut;
typedef long long LL;
const int N = 1e5+;
struct node
{
int x, y, z;
}t[N];
int cube[][][];///放木块的位置。
int st[*N*];///hash一个三维坐标的值为i+j*100+k*10000;
int outvalue = ;///表示自由块。
int flag[][][];///记录i+j*100+k*10000;
int dir[][] = {{,,},{,,},{,,},{-,,},{,-,},{,,-}};///向6个方向扩展。
int get(int i,int j,int k)
{
return i+j*+k*;
}
int Find(int x)
{
if(x==st[x]) return x;
return st[x] = Find(st[x]);
}
void Merge(int x,int y)
{
int fx = Find(x);
int fy = Find(y);
if(fy>fx){///保证小的数为根,是为了让outvalue=0这个值始终为根。方便判断是否是自由块。
st[fy] = fx;
}else
{
st[fx] = fy;
}
}
int main()
{
int T;
int n;
cin>>T;
while(T--)
{
scanf("%d",&n);
memset(cube, , sizeof cube);
for(int i = ; i <= n; i++){
scanf("%d%d%d",&t[i].x ,&t[i].y, &t[i].z);
cube[t[i].x][t[i].y][t[i].z] = ;
} for(int i = ; i <= ; i++){
for(int j = ; j <= ; j++){
for(int k = ; k <= ; k++){
flag[i][j][k] = get(i,j,k);
st[flag[i][j][k]] = flag[i][j][k];
}
}
}
for(int i = ; i <= ; i++){
for(int j = ; j <= ; j++){
for(int k = ; k <= ; k++){
if(cube[i][j][k]) continue;
for(int o = ; o < ; o++){
int x = i+dir[o][];
int y = j+dir[o][];
int z = k+dir[o][];
if(x<||x>||y<||y>||z>){///和超出数据范围的相邻,所以是自由块。
st[Find(flag[i][j][k])] = outvalue;
continue;
}
if(z<) continue;
if(cube[x][y][z]) continue;
Merge(flag[i][j][k],flag[x][y][z]);
}
}
}
}
int ans = ;
for(int i = n; i >= ; i--){
int tie = ;///是否和上一个木块相邻或者和地面相邻。
int out = ;///是否和自由块相邻。
for(int o = ; o < ; o++){
int x = t[i].x+dir[o][];
int y = t[i].y+dir[o][];
int z = t[i].z+dir[o][];
if(x<||x>||y<||y>||z>){
out = ;
continue;
}
if(z==){
tie = ; continue;
}
///!!!这里要注意判断顺序,不能直接cube[x][y][z].因为有些木块是已经被释放了的,被取走了。
if(Find(flag[x][y][z])==outvalue){///如果这个木块已经被释放或者自由块那么与out相连。
out = ;
}else
{
if(cube[x][y][z]){///没有被释放的木块。
tie = ;
}
}
}
if(tie&&out){
st[flag[t[i].x][t[i].y][t[i].z]] = outvalue;
for(int o = ; o < ; o++){
int x = t[i].x+dir[o][];
int y = t[i].y+dir[o][];
int z = t[i].z+dir[o][];
if(x<||x>||y<||y>||z>){
continue;
}
if(z==){
continue;
}
if(cube[x][y][z]){
continue;
}else
{
Merge(flag[t[i].x][t[i].y][t[i].z],flag[x][y][z]);
}
}
}else
{
ans = ; break;
}
}
printf("%s\n",ans?"Yes":"No"); }
return ;
}
hihoCoder #1291 : Building in Sandbox 逆向处理+并查集维护的更多相关文章
- ACM学习历程—Hihocoder 1291 Building in Sandbox(dfs && 离线 && 并查集)
http://hihocoder.com/problemset/problem/1291 前几天比较忙,这次来补一下微软笔试的最后一题,这题是这次微软笔试的第四题,过的人比较少,我当时在调试B题,没时 ...
- hihoCoder 1515 分数调查(带权并查集)
http://hihocoder.com/problemset/problem/1515 题意: 思路: 带权并查集的简单题,计算的时候利用向量法则即可. #include<iostream&g ...
- POJ2032 Building a Space Station(Kruskal)(并查集)
Building a Space Station Time Limit: 1000MS Memory Limit: 30000K Total Submissions: 7469 Accepte ...
- [HDOJ2818]Building Block(带权并查集,路径压缩)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2818 题意:有N个块,每次有两个操作: M x y表示把x所在的那一堆全部移到y所在的那一堆的下方. ...
- BZOJ 1015:[JSOI2008]星球大战starwar(逆向处理+并查集)
[JSOI2008]星球大战starwar 时间限制: 3 Sec 内存限制: 162 MB[题目描述] ...
- HihoCoder 1638 : 小Hi的天平 (2-sat+并查集)
描述 小Hi给小Ho邮寄了一个天平.收到天平后,小Ho想知道天平在运输过程中是否损坏,为此它准备了A类物品和B类物品共n个(可能只有A类物品,也可能只有B类物品),但无法确定一个物品是哪一类.A类物品 ...
- ZOJ 3261 Connections in Galaxy War(逆向并查集)
参考链接: http://www.cppblog.com/yuan1028/archive/2011/02/13/139990.html http://blog.csdn.net/roney_win/ ...
- 逆向并查集 hrbust 1913
#include<iostream> //由于拆除并查集的方法太难或者没有#include<cstdio> //可以先将所有没有拆的桥连接 再逆向操作 断开变成连接 反向输出# ...
- HDU - 4496 City 逆向并查集
思路:逆向并查集,逆向加入每一条边即可.在获取联通块数量的时候,直接判断新加入的边是否合并了两个集合,如果合并了说明联通块会减少一个,否则不变. AC代码 #include <cstdio> ...
随机推荐
- [Python爬虫] 之十二:Selenium +phantomjs抓取中的url编码问题
最近在抓取活动树网站 (http://www.huodongshu.com/html/find.html) 上数据时发现,在用搜索框输入中文后,点击搜索,phantomjs抓取数据怎么也抓取不到,但是 ...
- 《大规模web服务开发技术》笔记
前段时间趁空把<大规模web服务开发技术>这本书看完了,今天用一下午时间重新翻了一遍,把其中的要点记了下来,权当复习和备忘.由于自己对数据压缩.全文检索等还算比较熟,所以笔记内容主要涉及前 ...
- 记一次vue2项目部署nginx静态文件404解决过程
github上下的一个vue2的项目,运行可以的,webpack打包后,nginx请求报错: 发现路径很奇怪啊,所以果断来到build.js文件中看看是不是哪里不对. 已经一番引用查找: 发现在这里配 ...
- TortoiseSVN版本管理软件使用简单说明
很多时候在写一个小的项目不想使用github等工具,只想简单在本地搭建一个版本管理器.那么TortoiseSVN就非常适合. 第一步:下载TortoiseSVN,http://tortoisesvn. ...
- 算法笔记_073:哈密顿回路问题(Java)
目录 1 问题描述 2 解决方案 1 问题描述 什么是哈密顿回路? 引用自百度百科: 哈密顿图(哈密尔顿图)(英语:Hamiltonian path,或Traceable path)是一个无向图, ...
- webDriver API——第14部分Color Support
class selenium.webdriver.support.color.Color(red, green, blue, alpha=1) Bases: object Color conversi ...
- MyBatis SpringBoot2.0 数据库读写分离
1.自定义DataSource import org.springframework.jdbc.datasource.lookup.AbstractRoutingDataSource; /** * @ ...
- Win7系统与它的Virtualbox中安装的Ubuntu14.04共享信息的几种方法
虚拟机是每一个程序猿必备的工具.本文依据最新版VirtualBox用户手冊的提示,通过自己的亲自实践,给出了Win7系统与执行在当中的VirtualBox 5.0.2中的Ubuntu 14.04共享信 ...
- JS 错误处理与调试
在程序开发中难免会遇到一些错误,在成千上万的代码中去寻找错误非常明显相当于大海捞针.为此,每种计算机编程语言都要它独特的一套错误处理与调试机制.当然,JavaScript也不例外. 错误发生: 运行代 ...
- 【Linux】监控系统的状态
1.w命令 w命令是一个很强大的命令,该命令显示的信息比较丰富.以下是我的虚拟机w命令的一个展示 从上图我们可以看到: 第一行从左面开始显示的信息依次为:时间.系统运行时间.登陆用户数.平均负载 第二 ...