/**
题目:#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 逆向处理+并查集维护的更多相关文章

  1. ACM学习历程—Hihocoder 1291 Building in Sandbox(dfs && 离线 && 并查集)

    http://hihocoder.com/problemset/problem/1291 前几天比较忙,这次来补一下微软笔试的最后一题,这题是这次微软笔试的第四题,过的人比较少,我当时在调试B题,没时 ...

  2. hihoCoder 1515 分数调查(带权并查集)

    http://hihocoder.com/problemset/problem/1515 题意: 思路: 带权并查集的简单题,计算的时候利用向量法则即可. #include<iostream&g ...

  3. POJ2032 Building a Space Station(Kruskal)(并查集)

    Building a Space Station Time Limit: 1000MS   Memory Limit: 30000K Total Submissions: 7469   Accepte ...

  4. [HDOJ2818]Building Block(带权并查集,路径压缩)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2818 题意:有N个块,每次有两个操作: M x y表示把x所在的那一堆全部移到y所在的那一堆的下方. ...

  5. BZOJ 1015:[JSOI2008]星球大战starwar(逆向处理+并查集)

    [JSOI2008]星球大战starwar                                                时间限制: 3 Sec 内存限制: 162 MB[题目描述] ...

  6. HihoCoder 1638 : 小Hi的天平 (2-sat+并查集)

    描述 小Hi给小Ho邮寄了一个天平.收到天平后,小Ho想知道天平在运输过程中是否损坏,为此它准备了A类物品和B类物品共n个(可能只有A类物品,也可能只有B类物品),但无法确定一个物品是哪一类.A类物品 ...

  7. ZOJ 3261 Connections in Galaxy War(逆向并查集)

    参考链接: http://www.cppblog.com/yuan1028/archive/2011/02/13/139990.html http://blog.csdn.net/roney_win/ ...

  8. 逆向并查集 hrbust 1913

    #include<iostream> //由于拆除并查集的方法太难或者没有#include<cstdio> //可以先将所有没有拆的桥连接 再逆向操作 断开变成连接 反向输出# ...

  9. HDU - 4496 City 逆向并查集

    思路:逆向并查集,逆向加入每一条边即可.在获取联通块数量的时候,直接判断新加入的边是否合并了两个集合,如果合并了说明联通块会减少一个,否则不变. AC代码 #include <cstdio> ...

随机推荐

  1. scrapy-splash抓取动态数据例子八

    一.介绍 本例子用scrapy-splash抓取界面网站给定关键字抓取咨询信息. 给定关键字:个性化:融合:电视 抓取信息内如下: 1.资讯标题 2.资讯链接 3.资讯时间 4.资讯来源 二.网站信息 ...

  2. JNI_Android项目中调用.so动态库

    JNI_Android项目中调用.so动态库 2014年6月3日 JNI学习 參考:http://blog.sina.com.cn/s/blog_4298002e01013zk8.html 上一篇笔者 ...

  3. 使用airdrop进行文件共享

    使用airdrop进行文件共享 学习了: https://support.apple.com/zh-cn/HT203106 https://zh.wikihow.com/%E5%9C%A8Mac%E4 ...

  4. npm install 报错:node-pre-gyp ERR! 问题解决

    npm install报错问题解决 问题: E:\CodeSpace\GitlabTest\desktop>npm install > lifeccp-desktop@1.1.9 post ...

  5. Deep Learning论文笔记之(三)单层非监督学习网络分析

    Deep Learning论文笔记之(三)单层非监督学习网络分析 zouxy09@qq.com http://blog.csdn.net/zouxy09          自己平时看了一些论文,但老感 ...

  6. 算法笔记_124:密码脱落(Java)

    一 问题描述 X星球的考古学家发现了一批古代留下来的密码.这些密码是由A.B.C.D 四种植物的种子串成的序列.仔细分析发现,这些密码串当初应该是前后对称的(也就是我们说的镜像串).由于年代久远,其中 ...

  7. 投票ajax请求代码(点赞代码)

    function vote(url, arr) { jq.ajax({ cache: false, async: false, url: url, type: 'post', data: {info_ ...

  8. Linux内核部件分析 原子性操作atomic_t

    在任何处理器平台下,都会有一些原子性操作,供操作系统使用,我们这里只讲x86下面的.在单处理器情况下,每条指令的执行都是原子性的,但在多处理器情况下,只有那些单独的读操作或写操作才是原子性的.为了弥补 ...

  9. iOS UITableView表视图滚动隐藏UINavigationController导航栏

    UITableView 继承于UIScrollView 所以UIScrollView 的代理方法相同适用于UITableView 中 隐藏导航栏的方法为: self.navigationControl ...

  10. ICP备案的一些tips~

    1)一个单位是一个备案主体,只能有一个主体备案号: 2)一个企业下面可以有多个网站,依次在备案号后加-1 -2,以此类推,也叫网站备案号,每个网站只能有一个网站备案号.(所谓网站,不是指域名,也不是i ...