洛谷 P1514 引水入城

2021-07-26 12:10:59 字數 3190 閱讀 3034

題目概述

給定乙個n*m的矩陣,每個格仔代表高度,水只能向低處流。從最上面一排倒水,問最下面一排的每個格仔是否都有水流過。若是,輸出最少需在幾個格仔上倒水,若否,則輸出最下面一排有幾個格仔接不到水。

解題思路

可以證明,如果底排每個格仔都有水,那麼從頂部每個格仔倒下的水,在底部形成的一定是乙個連續的區間。

先用廣搜找出從每個格仔倒下水後在底部形成區間的左右端點(需要對能否全部有水進行特殊判斷),這樣問題就轉變成最小線段覆蓋問題了,用貪心即可。

注意:當n=1時,需要特殊判斷。

當且僅當某一頂部格仔高度不低於其兩邊的格仔時,才需要進行搜尋,其他點都是多餘的。

時間複雜度:o(n*m^2)

空間複雜度:o(n*m)

源程式

vara:array[0..505,0..505]of longint;

b:array[0..505,1..2]of longint;

c:array[0..270000,1..2]of longint;

d:array[0..505]of boolean;

f:array[0..505,1..2]of longint;

g:array[0..505,0..505]of longint;

n,m,i,j,top,tail,lb:longint;

procedure linex;

vari,j,jl,now,u,t:longint;

begin

jl:=0;

now:=0;

u:=0;

for i:=1 to m do

if b[i,1]<=b[i,2] then begin

inc(jl);

f[jl,1]:=b[i,1];

f[jl,2]:=b[i,2];

end;

for i:=1 to jl-1 do

for j:=i+1 to jl do

if f[i,1]>f[j,1] then begin

f[0]:=f[i];

f[i]:=f[j];

f[j]:=f[0];

end;

while now<=m do

begin

inc(now);

if now>m then break;

j:=0;

for i:=1 to jl do

begin

if f[i,1]>now then break;

if f[i,2]>j then j:=f[i,2];

end;

inc(u);

now:=j;

end;

writeln(1);

writeln(u);

end;

procedure search(p:longint);

varmaxl,maxr:longint;

begin

maxl:=9999;

maxr:=-2;

top:=0;

tail:=1;

c[1,1]:=1;

c[1,2]:=p;

while top<=tail do

begin

inc(top);

if top>tail then break;

g[c[top,1],c[top,2]]:=i;

if (c[top,1]-1>0)and(a[c[top,1]-1,c[top,2]]i) then

begin

inc(tail);

c[tail,1]:=c[top,1]-1;

c[tail,2]:=c[top,2];

if c[tail,1]=n then begin

if d[c[tail,2]]=false then begin

d[c[tail,2]]:=true;

dec(lb);

end;

if c[tail,2]>maxr then maxr:=c[tail,2];

if c[tail,2]i) then

begin

inc(tail);

c[tail,1]:=c[top,1]+1;

c[tail,2]:=c[top,2];

if c[tail,1]=n then begin

if d[c[tail,2]]=false then begin

d[c[tail,2]]:=true;

dec(lb);

end;

if c[tail,2]>maxr then maxr:=c[tail,2];

if c[tail,2]0)and(a[c[top,1],c[top,2]-1]i) then

begin

inc(tail);

c[tail,1]:=c[top,1];

c[tail,2]:=c[top,2]-1;

if c[tail,1]=n then begin

if d[c[tail,2]]=false then begin

d[c[tail,2]]:=true;

dec(lb);

end;

if c[tail,2]>maxr then maxr:=c[tail,2];

if c[tail,2]i) then

begin

inc(tail);

c[tail,1]:=c[top,1];

c[tail,2]:=c[top,2]+1;

if c[tail,1]=n then begin

if d[c[tail,2]]=false then begin

d[c[tail,2]]:=true;

dec(lb);

end;

if c[tail,2]>maxr then maxr:=c[tail,2];

if c[tail,2]maxr then maxr:=p;

if p=a[1,i-1])and(a[1,i]>=a[1,i+1]) then search(i);

if lb>0 then begin

writeln(0);

writeln(lb);

endelse linex;

end.

洛谷 P1514 引水入城

題目描述 在乙個遙遠的國度,一側是風景秀美的湖泊,另一側則是漫無邊際的沙漠。該國的行政區劃十分特殊,剛好構成乙個n 行m 列的矩形,如上圖所示,其中每個格仔都代表一座城市,每座城市都有乙個海拔高度。為了使居民們都盡可能飲用到清澈的湖水,現在要在某些城市建造水利設施。水利設施有兩種,分別為蓄水廠和輸水...

洛谷P1514 引水入城

想用搜尋水一水,結果一水就是一下午emmm 用第一層的點去更新其他層的點,並記錄能更新到的最遠的端點,然後下面判斷是否最底層都能到達,都能到達就通過記錄的左右端點來更新,使在最少使用的情況下框到最大的範圍就行了 by acermo include include include include in...

洛谷 P1514 引水入城

在乙個遙遠的國度,一側是風景秀美的湖泊,另一側則是漫無邊際的沙漠。該國的行政區劃十分特殊,剛好構成乙個nn 行 times m m 列的矩形,如上圖所示,其中每個格仔都代表一座城市,每座城市都有乙個海拔高度。為了使居民們都盡可能飲用到清澈的湖水,現在要在某些城市建造水利設施。水利設施有兩種,分別為蓄...