引水入城

 

描述

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

为了使居民们都尽可能饮用到清澈的湖水,现在要在某些城市建造水利设施。水利设施有两种,分别为蓄水厂和输水站。蓄水厂的功能是利用水泵将湖泊中的水抽取到所在城市的蓄水池中。因此,只有与湖泊毗邻的第1行的城市可以建造蓄水厂。而输水站的功能则是通过输水管线利用高度落差,将湖水从高处向低处输送。故一座城市能建造输水站的前提,是存在比它海拔更高且拥有公共边的相邻城市,已经建有水利设施。

由于第N行的城市靠近沙漠,是该国的干旱区,所以要求其中的每座城市都建有水利设施。那么,这个要求能否满足呢?如果能,请计算最少建造几个蓄水厂;如果不能,求干旱区中不可能建有水利设施的城市数目。

格式

输入格式

输入文件的每行中两个数之间用一个空格隔开。

输入的第一行是两个正整数N和M,表示矩形的规模。

接下来N行,每行M个正整数,依次代表每座城市的海拔高度。

输出格式

输出有两行。如果能满足要求,输出的第一行是整数1,第二行是一个整数,代表最少建造几个蓄水厂;如果不能满足要求,输出的第一行是整数0,第二行是一个整数,代表有几座干旱区中的城市不可能建有水利设施。

样例1

样例输入1

2 5
9 1 5 4 3
8 7 6 1 2

样例输出1

1
1

限制

每个测试点1s

提示

本题共有10个测试数据,每个数据的范围如下表所示:
测试数据编号 能否满足要求 N M
1 不能 ≤ 10 ≤ 10
2 不能 ≤ 100 ≤ 100
3 不能 ≤ 500 ≤ 500
4 能 = 1 ≤ 10
5 能 ≤ 10 ≤ 10
6 能 ≤ 100 ≤ 20
7 能 ≤ 100 ≤ 50
8 能 ≤ 100 ≤ 100
9 能 ≤ 200 ≤ 200
10 能 ≤ 500 ≤ 500
对于所有的10个数据,每座城市的海拔高度都不超过10^6。

来源

noip2010提高组复赛

 

做实验室训练赛的时候唯一没做出来的题。。虽然我想到了这个贪心策略但是由于出题人题面有点问题所以没有写orz。
友情链接我校OJ同样的一题:林喵喵的炸弹攻击
首先我们对每个点做个bfs或dfs就能得出最终最后一行是否完全被覆盖。关键在于第二个问题:怎么让蓄水站最少?
建立在最后一行可以被完全覆盖的基础上,我们发觉每个蓄水站的可达区域是一个底边为沙漠边的大块。因此通过脑补我发觉第一行每个位置的蓄水站能覆盖的最后一行的城市肯定是连续的一段。通过反证法可以证明这个论点。
然后对于蓄水站最少这个问题,我们就转化成了怎样用最少的线段来覆盖整条线段。
这个是一个经典问题,鉴于500的量直接排序完贪一波,不亏。
 #include<bits/stdc++.h>
#define clr(x) memset(x,0,sizeof(x))
#define clr_1(x) memset(x,-1,sizeof(x))
#define LL long long
#define INF 0x3f3f3f3f
#define mod 000000007
#define next nexted
using namespace std;
const int N=5e2+;
int dirx[]={,,,-};
int diry[]={,-,,};
int gmap[N][N];
bool inf[N][N];
bool tag[N];
int n,m,k,ans,lt,rt,mx,p;
struct seg
{
int l,r;
}segt[N];
struct pos
{
int x,y;
}now,next;
queue<pos> que;
bool cmp(seg &a,seg &b)
{
if(a.l==b.l) return a.r>b.r;
return a.l<b.l;
}
void bfs(int tg)
{
clr(inf);
int lt=;rt=;
now.x=;
now.y=tg;
que.push(now);
inf[now.x][now.y]=;
while(!que.empty())
{
now=que.front();
que.pop();
if(now.x==n)
{
if(now.y<lt) lt=now.y;
if(now.y>rt) rt=now.y;
tag[now.y]=;
}
for(int i=;i<;i++)
{
next.x=now.x+dirx[i];
next.y=now.y+diry[i];
if(!inf[next.x][next.y] && gmap[next.x][next.y]<gmap[now.x][now.y])
{
que.push(next);
inf[next.x][next.y]=;
}
}
}
segt[tg].l=lt;
segt[tg].r=rt;
return ;
}
int main()
{
while(scanf("%d%d",&n,&m)!=EOF)
{
for(int i=;i<=n;i++)
for(int j=;j<=m;j++)
scanf("%d",&gmap[i][j]);
for(int i=;i<=m+;i++)
gmap[][i]=gmap[n+][i]=INF;
for(int i=;i<=n+;i++)
gmap[i][]=gmap[i][m+]=INF;
clr(tag);
for(int i=;i<=m;i++)
bfs(i);
ans=;
for(int i=;i<=m;i++)
if(!tag[i]) ans++;
if(ans)
{
printf("0\n%d\n",ans);
continue;
}
sort(segt+,segt+m+,cmp);
lt=segt[].l;
rt=segt[].r;
ans=;
p=;
while(rt<m)
{
mx=;
k=p;
for(int i=k+;i<=m;i++)
{
if(segt[i].l<=lt) continue;
if(segt[i].l>rt+) break;
if(segt[i].r>=mx)
{
mx=segt[i].r;
p=i;
}
}
++ans;
lt=segt[p].l;
rt=segt[p].r;
}
printf("1\n%d\n",ans);
}
return ;
}

vijos p1777 引水入城(bfs+贪心)的更多相关文章

  1. NOIP2010_T4_引水入城 bfs+贪心

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

  2. noip2010 引水入城 bfs+贪心

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

  3. luogu 1066 引水入城(bfs+贪心)

    90分,有一个点TLE.... 首先可以证明一个东西,如果从上面一排的某个点bfs一次到最下面一排的饮水点不是一个区间的话,那么最后一定所有饮水点不会被覆盖完的. 证明考虑反证法. 所以从上面一排的每 ...

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

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

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

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

  6. luogu1514 [NOIp2010]引水入城 (bfs+记忆化搜索)

    我们先bfs一下看看是否能到最底下的所有点 如果不能的话,直接把不能到的那几个数一数就行了 如果能的话: 可以发现(并不可以)某格能到达的最底下的格子一定是一个连续的区间 (因为如果不连续的话,我们先 ...

  7. LUOGU P1514 引水入城 (bfs)

    传送门 解题思路 拉了很长的战线,换了好几种写法终于过了..首先每个蓄水场一定是对沙漠造成连续一段的贡献,所以可以$bfs$出每种状态,然后做一次最小区间覆盖,但这样的复杂度有点高.就每次只搜那些比左 ...

  8. luoguP1514 引水入城 题解(NOIP2010)(Bfs+贪心)

    P1514 引水入城  题目 #include<iostream> #include<cstdlib> #include<cstdio> #include<c ...

  9. 引水入城 2010年NOIP全国联赛提高组(bfs+贪心)

    1066 引水入城 2010年NOIP全国联赛提高组  时间限制: 1 s  空间限制: 128000 KB  题目等级 : 钻石 Diamond     题目描述 Description 在一个遥远 ...

随机推荐

  1. windows下 nginx安装 使用

    介绍 Nginx (engine x) 是一个高性能的HTTP和反向代理服务器. 反向代理(Reverse Proxy)方式是指以代理服务器来接受internet上的连接请求,然后将请求转发给内部网络 ...

  2. perl HTML::LinkExtor模块(1)

    use LWP::Simple; use HTML::LinkExtor; $html = get("http://www.baidu.com"); $link = HTML::L ...

  3. Java面试基础知识1

    1.动态绑定是指在执行期间判断所引用对象的实际类型,根据其实际的类型调用其相应的方法. 2.在将超类转换为子类之前,应该使用instanceof进行检查. 3.包含一个或者多个抽象方法的类本身必须被声 ...

  4. kimbits_USACO

    StringsobitsKim Schrijvers Consider an ordered set S of strings of N (1 <= N <= 31) bits. Bits ...

  5. 【数位dp入门】【HDU2089】62

    为了我的点歪的技能树…… 所以开始补一些sb的东西…… #include<bits/stdc++.h> typedef long long ll; using namespace std; ...

  6. 2017多校第6场 HDU 6096 String AC自动机

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6096 题意:给了一些模式串,然后再给出一些文本串的不想交的前后缀,问文本串在模式串的出现次数. 解法: ...

  7. HTML 知识点总结

    HTML基本语法 HTML标签 单标签 <标签名>或<标签名 /> 双标签 <标签名>内容</标签名> 跟标签也叫元素(根元素) 属性 属性属于标签 一 ...

  8. thinkphp5 消息队列thinkphp-queue扩展

    1.简介 thinkphp-queue是thinkphp的一个第三方扩展, 内置了 Redis,Database,Topthink ,Sync这四种驱动,推荐使用redis 2. 下载 和安装 com ...

  9. Eclipse中部署ES源码运行

    https://stackoverflow.com/questions/40924671/how-to-build-elasticsearch-source-code-using-gradle Gra ...

  10. 简写代码:当变量为false时['',false,null,undefined,0,NaN]时,返回默认值

    当变量为'',false,null,undefined,0,NaN时,返回默认值 var a='' a || 'hello world'   "hello world" var a ...