我们先把简单的不能搞死,具题意可证:每个蓄水长的管辖区域一定是连续的。
证明:既然我们已经能了那么我们就可以说如果这个区间不是连续的那我们取出这个区间中间阻隔开的那一段,那么对于这一整个区间来说水源不可能来自两边那么一定至少有一条直通蓄水厂的路连其上一点,那么对于连着的那个蓄水厂a,以及我们造成此区间的蓄水厂b,b一定不是a,b若在a的左边则无法到达右边,若b在a的右边则无法到达左边,因此移动是连续的。由于数据中有一个一行的(既邻水又临漠),我要说一下,对于这个结论显然成立。
那么我们既然知道了每个蓄水厂的管辖范围我们进行右端点贪心即可。

#include<cstdio>
#include<bitset>
#include<algorithm>
#include<vector>
#define N 505
using namespace std;
inline int read()
{
int sum=;
char ch=getchar();
while(ch<''||ch>'')ch=getchar();
while(ch>=''&&ch<='')
{
sum=(sum<<)+(sum<<)+ch-'';
ch=getchar();
}
return sum;
}
struct Tr
{
int to,next;
}c[N*N*];
int head[N*N],t,kin[N*N];
bool v[N*N];
bitset<N> ctr[N];
int n,m;
int h[N][N];
inline int get(int x,int y)
{
return (x-)*m+y;
}
inline void add(int x,int y)
{
c[++t].to=y;
c[t].next=head[x];
head[x]=t;
}
void Init()
{
n=read(),m=read();
for(int i=;i<=n;i++)
for(int j=;j<=m;j++)
h[i][j]=read();
for(int i=;i<=n;i++)
for(int j=;j<=m;j++)
{
if(h[i+][j]<h[i][j]&&i+<=n)add(get(i,j),get(i+,j));
if(h[i-][j]<h[i][j]&&i->)add(get(i,j),get(i-,j));
if(h[i][j+]<h[i][j]&&j+<=m)add(get(i,j),get(i,j+));
if(h[i][j-]<h[i][j]&&j->)add(get(i,j),get(i,j-));
}
for(int i=;i<=m;i++)
kin[get(,i)]=,kin[get(n,i)]=;
}
int hol=;
void jud(int x)
{
if(v[x])return;
if(kin[x]==)hol++;
v[x]=;
for(int i=head[x];i;i=c[i].next)
jud(c[i].to);
}
bool Jud()
{
for(int i=;i<=m;i++)
jud(i);
if(hol<m)
{
printf("");
printf("\n");
printf("%d\n",m-hol);
return ;
}
return ;
}
bool over[N];
int vo[N*N];
void dfs(int x,int now)
{
if(vo[x]==now)return;
vo[x]=now;
if(kin[x]==&&x!=now)
over[x]=;
if(kin[x]==)
ctr[now][x-(n-)*m]=;
for(int i=head[x];i;i=c[i].next)
dfs(c[i].to,now);
}
struct DP
{
int l,r;
}dp[N];
int Min,ans,NN=;
int bre[N];
bool Now[N];
int comp(const DP a,const DP b)
{
return a.l<b.l;
}
void Dp()
{
NN--;
sort(dp+,dp+NN+,comp);
int now=,Ans=;
for(int i=;i<=NN;i++)
{
if(dp[i].l>now)
{
ans++;
now=Ans+;
if(now>m)break;
}
if(dp[i].r>Ans)
Ans=dp[i].r;
}
if(now<=m)
ans++;
}
void work()
{
for(int i=;i<=m;i++)
if(!over[i])
dfs(i,i);
for(int i=;i<=m;i++)
if(!over[i])
bre[++Min]=i;
for(int i=;i<=Min;i++)
{
int no=;
for(int j=;j<=m;j++)
{
if(no==&&ctr[bre[i]][j]==)
{
no=;
dp[NN].l=j;
}
if(no==&&ctr[bre[i]][j]==)
{
dp[NN].r=j-;
break;
}
}
if(no==)
{
i--;
Min--;
continue;
}
if(dp[i].r==)
dp[NN].r=m;
NN++;
}
Dp();
printf("");
printf("\n");
printf("%d\n",ans);
}
int main()
{
Init();
if(Jud())return ;
work();
return ;
}

NOIP2010 引水入城 贪心+DFS的更多相关文章

  1. NOIP2010引水入城[BFS DFS 贪心]

    题目描述 在一个遥远的国度,一侧是风景秀美的湖泊,另一侧则是漫无边际的沙漠.该国的行政区划十分特殊,刚好构成一个N 行M 列的矩形,如上图所示,其中每个格子都代表一座城市,每座城市都有一个海拔高度. ...

  2. [NOIP2010] 引水入城 贪心 + 记忆化搜索

    ---题面--- 题解: 本蒟蒻并没有想到bfs的做法,,,, 只会dfs了 首先我们需要知道一个性质. 我们设k[i].l 为在i点建立水库可以支援到的最左边的城市,k[i].r为最右边的. 那么点 ...

  3. 521. [NOIP2010] 引水入城 cogs

    521. [NOIP2010] 引水入城 ★★★   输入文件:flow.in   输出文件:flow.out   简单对比时间限制:1 s   内存限制:128 MB 在一个遥远的国度,一侧是风景秀 ...

  4. NOIP2010 引水入城

    4引水入城 题目描述 在一个遥远的国度,一侧是风景秀美的湖泊,另一侧则是漫无边际的沙漠.该国的行政区划十分特殊,刚好构成一个N 行M 列的矩形,如上图所示,其中每个格子都代表一座城市,每座城市都有一个 ...

  5. noip2010 引水入城 bfs+贪心

    如果能够实现,每个河边的城市对应的控制区域一定是一条线段. 所以直接bfs每个河边的城市,贪心线段的右端点 #include<cstdio> #include<cstring> ...

  6. Luogu1514 NOIP2010 引水入城 BFS、贪心

    传送门 NOIP的题目都难以写精简题意 考虑最上面一排的某一个点对最下面一排的影响是什么样的,不难发现必须要是一段连续区间才能够符合题意. 如果不是一段连续区间,意味着中间某一段没有被覆盖的部分比周围 ...

  7. NOIP2010 引水入城 题解

    http://www.rqnoj.cn/problem/601 今天发现最小区间覆盖竟然是贪心,不用DP!于是我又找到这题出来撸了一发. 要找到最上面每个城市分别能覆盖最下面哪些城市,如果最下面有城市 ...

  8. noip2010引水入城

    https://www.zybuluo.com/ysner/note/1334997 这道题fst了 题面 戳我 解析 我一开始的想法是,按照高度给第一行排序,然后贪心地选取目前到不了的,高度最高的第 ...

  9. noip 2010 引水入城 贪心 + 搜索

    不难分析出如果有解则每个蓄水厂所能覆盖到的干旱城市一定是连续的.否则,中间那些没被覆盖的部分永远都不能被覆盖到. 当然,每个蓄水厂所覆盖的城市有可能不连续,不过既然有解,则一定都是连续的.我们可以开一 ...

随机推荐

  1. mysql 5.7 配置初始化及修改 ROOT 用户密码

    1.修改配置文件 my.ini 放在 mysql\bin [mysqld] basedir=C:\Mysql datadir=C:\Mysql\data port=3306 # server_id = ...

  2. BAT批处理

    常用命令 查看目录内容命令dir 指定可执行文件搜索目录path 创建目录命令md 打开指定目录命令cd 删除当前指定的子目录命令rd 改变当前盘符命令d: 文件复制命令copy 显示文本文件内容命令 ...

  3. maven中settings文件的配置

    鉴于上一个博客写的maven打包,读者老爷们可能找不到settings文件的配置,这里专门附上settings文件的配置: 有的settings文件只含有一些空标签,需要手动去配置. <?xml ...

  4. ssrf小记

    SSRF(Server-Side Request Forgery, 服务端请求伪造),攻击者伪造服务端发起的请求并执行,从而获得一些数据或进行攻击 一.危害 1.对内网的端口和服务进行扫描,对主机本地 ...

  5. Android开发——View绘制过程源码解析(一)

    )UNSPECIFIED:表示View可以设置成任意的大小,没有任何限制.这种情况比较少见. 2. MeasureSpec的生成过程 2.1 顶级View的MeasureSpec // desired ...

  6. 深度分析如何在Hadoop中控制Map的数量(摘抄)

    很多文档中描述,Mapper的数量在默认情况下不可直接控制干预,因为Mapper的数量由输入的大小和个数决定.在默认情况下,最终input占据了多少block,就应该启动多少个Mapper.如果输入的 ...

  7. Linux(centos)搭建SVN服务器完美方案及遇到的问题--费元星站长

    QQ:971751392 (欢迎交流) linux搭建SVN服务器 安装步骤如下: 1.yum install subversion   2.输入rpm -ql subversion查看安装位置,如下 ...

  8. DDD领域驱动设计基本理论知识总结(转)

    领域驱动设计之领域模型 为什么建立一个领域模型是重要的 领域通用语言(UBIQUITOUS LANGUAGE) 将领域模型转换为代码实现的最佳实践 领域建模时思考问题的角度 领域驱动设计的经典分层架构 ...

  9. ES6 语法糖

    重新认识ES6中的语法糖:https://segmentfault.com/a/1190000010159725

  10. #Spring实战第二章学习笔记————装配Bean

    Spring实战第二章学习笔记----装配Bean 创建应用对象之间协作关系的行为通常称为装配(wiring).这也是依赖注入(DI)的本质. Spring配置的可选方案 当描述bean如何被装配时, ...