题目描述

我们憨厚的USACO主人公农夫约翰(Farmer John)以无法想象的运气,在他生日那天收到了一份特别的礼物:一张“幸运爱尔兰”(一种彩票)。结果这张彩票让他获得了这次比赛唯一的奖品——坐落于爱尔兰郊外的一座梦幻般的城堡!

喜欢吹嘘的农夫约翰立刻回到有着吹嘘传统的威斯康辛老家开始吹嘘了, 农夫约翰想要告诉他的奶牛们关于他城堡的一切。他需要做一些吹嘘前的准备工作:比如说知道城堡有多少个房间,每个房间有多大。另外,农夫约翰想要把一面单独的墙(指两个单位间的墙)拆掉以形成一个更大的房间。 你的工作就是帮农夫约翰做以上的准备,算出房间数与房间的大小。

城堡的平面图被划分成M*N(1 <=M,N<=50)个正方形的单位,一个这样的单位可以有0到4面墙环绕。城堡周围一定有外墙环绕以遮风挡雨。(就是说平面图的四周一定是墙。)

请仔细研究下面这个有注解的城堡平面图:

友情提示,这个城堡的平面图是7×4个单位的。一个“房间”的是平面图中一个由“#”、“-”、“|”围成的格子(就是图里面的那一个个的格子)。比如说这个样例就有5个房间。(大小分别为9、7、3、1、8个单位(排名不分先后))

移去箭头所指的那面墙,可以使2个房间合为一个新房间,且比移去其他墙所形成的房间都大。(原文为:Removing the wall marked by the arrow merges a pair of rooms to make the largest possible room that can be made by removing a single wall. )

城堡保证至少有2个房间,而且一定有一面墙可以被移走。

输入输出格式

输入格式:

第一行有两个整数:M和N 城堡的平面图用一个由数字组成的矩阵表示,一个数字表示一个单位,矩阵有N行M列。输入与样例的图一致。

每一个单位的数字告诉我们这个单位的东西南北是否有墙存在。每个数字是由以下四个整数的某个或某几个或一个都没有加起来的。

1: 在西面有墙

2: 在北面有墙

4: 在东面有墙

8: 在南面有墙

城堡内部的墙会被规定两次。比如说(1,1)南面的墙,亦会被标记为(2,1)北面的墙。

输出格式:

输出包含如下4行:

第 1 行: 城堡的房间数目。

第 2 行: 最大的房间的大小

第 3 行: 移除一面墙能得到的最大的房间的大小

第 4 行: 移除哪面墙可以得到面积最大的新房间。

选择最佳的墙来推倒。有多解时选最靠西的,仍然有多解时选最靠南的。同一格子北边的墙比东边的墙更优先。

用该墙的南邻单位的北墙或西邻单位的东墙来表示这面墙,方法是输出邻近单位的行数、列数和墙的方位("N"(北)或者"E"(东))。

输入输出样例

输入样例#1: 复制

  1. 7 4
  2. 11 6 11 6 3 10 6
  3. 7 9 6 13 5 15 5
  4. 1 10 12 7 13 7 5
  5. 13 11 10 8 10 12 13
输出样例#1: 复制

  1. 5
  2. 9
  3. 16
  4. 4 1 E

说明

USACO 2.1

翻译来自NOCOW

  1. #include<cstdio>
  2. #include<cstring>
  3. #include<iostream>
  4. #include<algorithm>
  5. using namespace std;
  6. int n,m;
  7. char ansz;
  8. int ansx,ansy,ans;
  9. int fa[],sum[];
  10. int get(int x,int y){
  11. return (x-)*m+y;
  12. }
  13. int find(int x){
  14. if(fa[x]==x) return x;
  15. else return fa[x]=find(fa[x]);
  16. }
  17. void add(int x,int y){
  18. int dx=find(x),dy=find(y);
  19. if(dx==dy) return ;
  20. else fa[dy]=dx;
  21. }
  22. void work(int x,int y,int num){
  23. int id=get(x,y);
  24. if(num==){
  25. if(x->=) add(id,get(x-,y));
  26. if(x+<=n) add(id,get(x+,y));
  27. if(y+<=m) add(id,get(x,y+)); }
  28. else if(num==){
  29. if(x+<=n) add(id,get(x+,y));
  30. if(y->=) add(id,get(x,y-));
  31. if(y+<=m) add(id,get(x,y+)); }
  32. else if(num==){
  33. if(x+<=n) add(id,get(x+,y));
  34. if(x->=) add(id,get(x-,y));
  35. if(y->=) add(id,get(x,y-)); }
  36. else if(num==){
  37. if(x->=) add(id,get(x-,y));
  38. if(y->=) add(id,get(x,y-));
  39. if(y+<=m) add(id,get(x,y+)); }
  40. else if(num==){
  41. if(x+<=n) add(id,get(x+,y));
  42. if(y+<=m) add(id,get(x,y+)); }
  43. else if(num==){
  44. if(x+<=n) add(id,get(x+,y));
  45. if(x->=) add(id,get(x-,y)); }
  46. else if(num==){
  47. if(x+<=n) add(id,get(x+,y));
  48. if(y->=) add(id,get(x,y-)); }
  49. else if(num==){
  50. if(x->=) add(id,get(x-,y));
  51. if(y+<=m) add(id,get(x,y+)); }
  52. else if(num==){
  53. if(y->=) add(id,get(x,y-));
  54. if(y+<=m) add(id,get(x,y+)); }
  55. else if(num==){
  56. if(x->=) add(id,get(x-,y));
  57. if(y->=) add(id,get(x,y-));
  58. }
  59. else if(num==){
  60. if(x+<=n) add(id,get(x+,y));
  61. }
  62. else if(num==){
  63. if(y+<=m) add(id,get(x,y+));
  64. }
  65. else if(num==){
  66. if(x->=) add(id,get(x-,y));
  67. }
  68. else if(num==){
  69. if(y->=) add(id,get(x,y-));
  70. }
  71. }
  72. int main(){
  73. scanf("%d%d",&m,&n);
  74. for(int i=;i<=(n+)*(m+);i++) fa[i]=i;
  75. for(int i=;i<=n;i++)
  76. for(int j=;j<=m;j++){
  77. int num;scanf("%d",&num);
  78. work(i,j,num);
  79. }
  80. for(int i=;i<=n*m;i++)
  81. sum[find(i)]++;
  82. int ans1=,ans2=;
  83. for(int i=;i<=n*m;i++){
  84. if(find(i)==i) ans1++;
  85. ans2=max(ans2,sum[fa[i]]);
  86. }
  87. cout<<ans1<<endl<<ans2<<endl;
  88. for(int i=;i<=n;i++)
  89. for(int j=;j<=m;j++){
  90. if(i->=){
  91. int x=get(i,j),y=get(i-,j);
  92. int dx=find(x),dy=find(y);
  93. if(dx!=dy){
  94. if(sum[dx]+sum[dy]>ans){
  95. ans=sum[dx]+sum[dy];
  96. ansx=i;ansy=j;ansz='N';
  97. }
  98. else if(sum[dx]+sum[dy]==ans){
  99. if(j<ansy){ ansx=i;ansy=j;ansz='N'; }
  100. else if(j==ansy&&i>ansx){ ansx=i;ansy=j;ansz='N'; }
  101. }
  102. }
  103. }
  104. if(j->=){
  105. int x=get(i,j),y=get(i,j-);
  106. int dx=find(x),dy=find(y);
  107. if(dx!=dy){
  108. if(sum[dx]+sum[dy]>ans){
  109. ans=sum[dx]+sum[dy];
  110. ansx=i;ansy=j-;ansz='E';
  111. }
  112. else if(sum[dx]+sum[dy]==ans){
  113. if(j-<ansy){ ansx=i;ansy=j-;ansz='E'; }
  114. else if(j-==ansy&&i>ansx){ ansx=i;ansy=j-;ansz='E'; }
  115. }
  116. }
  117. }
  118. if(i+<=n){
  119. int x=get(i,j),y=get(i+,j);
  120. int dx=find(x),dy=find(y);
  121. if(dx!=dy){
  122. if(sum[dx]+sum[dy]>ans){
  123. ans=sum[dx]+sum[dy];
  124. ansx=i+;ansy=j;ansz='N';
  125. }
  126. else if(sum[dx]+sum[dy]==ans){
  127. if(j<ansy){ ansx=i+;ansy=j;ansz='N'; }
  128. else if(j==ansy&&i+>ansx){ ansx=i+;ansy=j;ansz='N'; }
  129. }
  130. }
  131. }
  132. if(j+<=m){
  133. int x=get(i,j),y=get(i,j+);
  134. int dx=find(x),dy=find(y);
  135. if(dx!=dy){
  136. if(sum[dx]+sum[dy]>ans){
  137. ans=sum[dx]+sum[dy];
  138. ansx=i;ansy=j;ansz='E';
  139. }
  140. else if(sum[dx]+sum[dy]==ans){
  141. if(j<ansy){ ansx=i;ansy=j;ansz='E'; }
  142. else if(j==ansy&&i>ansx){ ansx=i;ansy=j;ansz='E'; }
  143. }
  144. }
  145. }
  146. }
  147. cout<<ans<<endl<<ansx<<" "<<ansy<<" "<<ansz;
  148. }

74分

漏下了四面都没有墙的 也就是输入为0的。

  1. /*用并查集处理所有情况的联通块*/
  2. #include<cstdio>
  3. #include<cstring>
  4. #include<iostream>
  5. #include<algorithm>
  6. using namespace std;
  7. int n,m;
  8. char ansz;
  9. int ansx,ansy,ans;
  10. int fa[],sum[];
  11. int get(int x,int y){
  12. return (x-)*m+y;
  13. }
  14. int find(int x){
  15. if(fa[x]==x) return x;
  16. else return fa[x]=find(fa[x]);
  17. }
  18. void add(int x,int y){
  19. int dx=find(x),dy=find(y);
  20. if(dx==dy) return ;
  21. else fa[dy]=dx;
  22. }
  23. void work(int x,int y,int num){
  24. int id=get(x,y);
  25. if(num==){
  26. if(x->=) add(id,get(x-,y));
  27. if(x+<=n) add(id,get(x+,y));
  28. if(y+<=m) add(id,get(x,y+));
  29. if(y->=) add(id,get(x,y-)); }
  30. else if(num==){
  31. if(x->=) add(id,get(x-,y));
  32. if(x+<=n) add(id,get(x+,y));
  33. if(y+<=m) add(id,get(x,y+)); }
  34. else if(num==){
  35. if(x+<=n) add(id,get(x+,y));
  36. if(y->=) add(id,get(x,y-));
  37. if(y+<=m) add(id,get(x,y+)); }
  38. else if(num==){
  39. if(x+<=n) add(id,get(x+,y));
  40. if(x->=) add(id,get(x-,y));
  41. if(y->=) add(id,get(x,y-)); }
  42. else if(num==){
  43. if(x->=) add(id,get(x-,y));
  44. if(y->=) add(id,get(x,y-));
  45. if(y+<=m) add(id,get(x,y+)); }
  46. else if(num==){
  47. if(x+<=n) add(id,get(x+,y));
  48. if(y+<=m) add(id,get(x,y+)); }
  49. else if(num==){
  50. if(x+<=n) add(id,get(x+,y));
  51. if(x->=) add(id,get(x-,y)); }
  52. else if(num==){
  53. if(x+<=n) add(id,get(x+,y));
  54. if(y->=) add(id,get(x,y-)); }
  55. else if(num==){
  56. if(x->=) add(id,get(x-,y));
  57. if(y+<=m) add(id,get(x,y+)); }
  58. else if(num==){
  59. if(y->=) add(id,get(x,y-));
  60. if(y+<=m) add(id,get(x,y+)); }
  61. else if(num==){
  62. if(x->=) add(id,get(x-,y));
  63. if(y->=) add(id,get(x,y-));
  64. }
  65. else if(num==){
  66. if(x+<=n) add(id,get(x+,y));
  67. }
  68. else if(num==){
  69. if(y+<=m) add(id,get(x,y+));
  70. }
  71. else if(num==){
  72. if(x->=) add(id,get(x-,y));
  73. }
  74. else if(num==){
  75. if(y->=) add(id,get(x,y-));
  76. }
  77. }
  78. int main(){
  79. freopen("testdata.in","r",stdin);
  80. scanf("%d%d",&m,&n);
  81. for(int i=;i<=(n+)*(m+);i++) fa[i]=i;
  82. for(int i=;i<=n;i++)
  83. for(int j=;j<=m;j++){
  84. int num;scanf("%d",&num);
  85. work(i,j,num);
  86. }
  87. for(int i=;i<=n*m;i++)
  88. sum[find(i)]++;
  89. int ans1=,ans2=;
  90. for(int i=;i<=n*m;i++){
  91. if(find(i)==i) ans1++;
  92. ans2=max(ans2,sum[fa[i]]);
  93. }
  94. cout<<ans1<<endl<<ans2<<endl;
  95. for(int i=;i<=n;i++)
  96. for(int j=;j<=m;j++){
  97. if(i->=){
  98. int x=get(i,j),y=get(i-,j);
  99. int dx=find(x),dy=find(y);
  100. if(dx!=dy){
  101. if(sum[dx]+sum[dy]>ans){
  102. ans=sum[dx]+sum[dy];
  103. ansx=i;ansy=j;ansz='N';
  104. }
  105. else if(sum[dx]+sum[dy]==ans){
  106. if(j<ansy){ ansx=i;ansy=j;ansz='N'; }
  107. else if(j==ansy&&i>ansx){ ansx=i;ansy=j;ansz='N'; }
  108. }
  109. }
  110. }
  111. if(j->=){
  112. int x=get(i,j),y=get(i,j-);
  113. int dx=find(x),dy=find(y);
  114. if(dx!=dy){
  115. if(sum[dx]+sum[dy]>ans){
  116. ans=sum[dx]+sum[dy];
  117. ansx=i;ansy=j-;ansz='E';
  118. }
  119. else if(sum[dx]+sum[dy]==ans){
  120. if(j-<ansy){ ansx=i;ansy=j-;ansz='E'; }
  121. else if(j-==ansy&&i>ansx){ ansx=i;ansy=j-;ansz='E'; }
  122. }
  123. }
  124. }
  125. if(i+<=n){
  126. int x=get(i,j),y=get(i+,j);
  127. int dx=find(x),dy=find(y);
  128. if(dx!=dy){
  129. if(sum[dx]+sum[dy]>ans){
  130. ans=sum[dx]+sum[dy];
  131. ansx=i+;ansy=j;ansz='N';
  132. }
  133. else if(sum[dx]+sum[dy]==ans){
  134. if(j<ansy){ ansx=i+;ansy=j;ansz='N'; }
  135. else if(j==ansy&&i+>ansx){ ansx=i+;ansy=j;ansz='N'; }
  136. }
  137. }
  138. }
  139. if(j+<=m){
  140. int x=get(i,j),y=get(i,j+);
  141. int dx=find(x),dy=find(y);
  142. if(dx!=dy){
  143. if(sum[dx]+sum[dy]>ans){
  144. ans=sum[dx]+sum[dy];
  145. ansx=i;ansy=j;ansz='E';
  146. }
  147. else if(sum[dx]+sum[dy]==ans){
  148. if(j<ansy){ ansx=i;ansy=j;ansz='E'; }
  149. else if(j==ansy&&i>ansx){ ansx=i;ansy=j;ansz='E'; }
  150. }
  151. }
  152. }
  153. }
  154. cout<<ans<<endl<<ansx<<" "<<ansy<<" "<<ansz;
  155. }

100分

洛谷 P1457 城堡 The Castle的更多相关文章

  1. 洛谷P1457 城堡 The Castle

    P1457 城堡 The Castle 137通过 279提交 题目提供者该用户不存在 标签USACO 难度提高+/省选- 提交  讨论  题解 最新讨论 暂时没有讨论 题目描述 我们憨厚的USACO ...

  2. 洛谷 P1457 城堡 The Castle 解题报告

    P1457 城堡 The Castle 题目描述 我们憨厚的USACO主人公农夫约翰(Farmer John)以无法想象的运气,在他生日那天收到了一份特别的礼物:一张"幸运爱尔兰" ...

  3. 洛谷—— P1457 城堡 The Castle

    https://www.luogu.org/problem/show?pid=1457 题目描述 我们憨厚的USACO主人公农夫约翰(Farmer John)以无法想象的运气,在他生日那天收到了一份特 ...

  4. 题解 洛谷P1457 【城堡 The Castle】

    这道题,看似很烦,无从下手,但其实只要用位运算和联通快就能水过了呀. 首先,输入:似乎大意是把一个数拆成二进数的相加,分别表示\((i,j)\)东南西北是否有墙.\(1\)表示西,\(2\)表示北,\ ...

  5. P1457 城堡 The Castle

    轻度中毒 原题 :The Castle 以下为题解部分:明明辣么简单的一道题,硬是搞了1.5h,WTF?以下列出本题的一些要点. 搜索(DFS)嘛,染色嘛,统计大小嘛,很容易想,也很更易处理. 接下来 ...

  6. P1457 城堡 The Castle 位运算+BFS+思维(难题,好题)

    题目描述 我们憨厚的USACO主人公农夫约翰(Farmer John)以无法想象的运气,在他生日那天收到了一份特别的礼物:一张"幸运爱尔兰"(一种彩票).结果这张彩票让他获得了这次 ...

  7. 洛谷P1263 宫廷守卫

    P1263 宫廷守卫 题目描述 从前有一个王国,这个王国的城堡是一个矩形,被分为M×N个方格.一些方格是墙,而另一些是空地.这个王国的国王在城堡里设了一些陷阱,每个陷阱占据一块空地. 一天,国王决定在 ...

  8. $loj10156/$洛谷$2016$ 战略游戏 树形$DP$

    洛谷loj Desription Bob 喜欢玩电脑游戏,特别是战略游戏.但是他经常无法找到快速玩过游戏的方法.现在他有个问题. 现在他有座古城堡,古城堡的路形成一棵树.他要在这棵树的节点上放置最少数 ...

  9. 洛谷1640 bzoj1854游戏 匈牙利就是又短又快

    bzoj炸了,靠离线版题目做了两道(过过样例什么的还是轻松的)但是交不了,正巧洛谷有个"大牛分站",就转回洛谷做题了 水题先行,一道傻逼匈牙利 其实本来的思路是搜索然后发现写出来类 ...

随机推荐

  1. iOS-UI控件之UITableView(四)- cell数据刷新

    TableView- 数据刷新 数据刷新 添加数据 删除数据 更改数据 全局刷新方法(最常用) [self.tableView reloadData]; // 屏幕上的所有可视的cell都会刷新一遍 ...

  2. asp IIS网站的配置(Win7下启用IIS7配置ASP运行环境)

    其实win7下的IIS7配置过程是非常简单的.下面让seo博客来详细的介绍一下win7下配置IIS7环境运行ASP网站的方法,以供初接触者参考   第一次在windows7下配置IIS,虽然有丰富的x ...

  3. bat获取注册表值

    @echo off Setlocal enabledelayedexpansion for /f "skip=2 delims=: tokens=1,*" %%i in ('reg ...

  4. webgl推荐书籍

    网址:https://www.douban.com/doulist/45940373/ webgl 来自: Pasu2017-04-17创建   2017-07-25更新   推荐 关注 2 人关注 ...

  5. element-ui iview-admin 都是基于vue的ui框架

    element-ui iview-admin 都是基于vue的ui框架

  6. 谈谈如何来查看GC日志

    一.首先来看一下JVM中的GC有哪几种类型? 1.-XX:UseSerialGC 虚拟机运行在Client模式的默认值,打开此开关参数后,使用Serial+Serial Old收集器组合进行垃圾收集. ...

  7. Win10上 visual studio设置为本地IIS运行网站时 必须以管理员身份加载项目的解决方法

    右键,选择“兼容性疑难解答”. 选择“疑难解答程序” 选择“该程序需要附加权限” 点击测试程序 点击下一步 选择 是,为此程序保存这些设置

  8. mac vim设置python语法高亮

    1 "显示行号  2 set nu  3   4 "设置缩进tabstop  5 set ts=4  6 set shiftwidth=4  7 set expandtab  8 ...

  9. rsync_ssh

    rsync -av -e "ssh" /data/wwwroot/a1 node2:/data/wwwroot/

  10. 并发-5CAS与AQS

    juc: java.util.concurrent 锁: 悲观锁:写的比较多,对数据的增删改,读(查)少.Lock 乐观锁:反之,读多写少.版本 并发编程之 CAS 的原理 什么是CAS CAS (c ...