洛谷 P2805 BZOJ 1565 植物大戰殭屍

2021-09-19 18:02:56 字數 2979 閱讀 6541

plants vs. zombies(pvz)是最近十分風靡的一款小遊戲。plants(植物)和zombies(殭屍)是遊戲的主角,其中plants防守,而zombies進攻。該款遊戲包含多種不同的挑戰系列,比如protect your brain、bowling等等。其中最為經典的,莫過於玩家通過控制plants來防守zombies的進攻,或者相反地由玩家通過控制zombies對plants發起進攻。

現在,我們將要考慮的問題是遊戲中zombies對plants的進攻,請注意,本題中規則與實際遊戲有所不同。遊戲中有兩種角色,plants和zombies,每個plant有乙個攻擊位置集合,它可以對這些位置進行保護;而zombie進攻植物的方式是走到植物所在的位置上並將其吃掉。

遊戲的地圖可以抽象為乙個n行m列的矩陣,行從上到下用0到n–1編號,列從左到右用0到m–1編號;在地圖的每個位置上都放有乙個plant,為簡單起見,我們把位於第r行第c列的植物記為pr, c。

plants分很多種,有攻擊類、防守類和經濟類等等。為了簡單的描述每個plant,定義score和attack如下:

score[pr, c]

zombie擊潰植物pr, c可獲得的能源。若score[pr, c]為非負整數,則表示擊潰植物pr, c可獲得能源score[pr, c],若為負數表示擊潰pr, c需要付出能源 -score[pr, c]。

attack[pr, c]

植物pr, c能夠對zombie進行攻擊的位置集合。

zombies必須從地圖的右側進入,且只能沿著水平方向進行移動。zombies攻擊植物的唯一方式就是走到該植物所在的位置並將植物吃掉。因此zombies的進攻總是從地圖的右側開始。也就是說,對於第r行的進攻,zombies必須首先攻擊pr, m-1;若需要對pr, c(0≤c在本題的設定中,plants的攻擊力是無窮大的,一旦zombie進入某個plant的攻擊位置,該zombie會被瞬間消滅,而該zombie沒有時間進行任何攻擊操作。因此,即便zombie進入了乙個plant所在的位置,但該位置屬於其他植物的攻擊位置集合,則zombie會被瞬間消滅而所在位置的植物則安然無恙(在我們的設定中,plant的攻擊位置不包含自身所在位置,否則你就不可能擊潰它了)。

zombies的目標是對plants的陣地發起進攻並獲得最大的能源收入。每一次,你可以選擇乙個可進攻的植物進行攻擊。本題的目標為,制定一套zombies的進攻方案,選擇進攻哪些植物以及進攻的順序,從而獲得最大的能源收入。

輸入格式:

輸入檔案pvz.in的第一行包含兩個整數n, m,分別表示地圖的行數和列數。

接下來n×m行描述每個位置上植物的資訊。第r×m + c + 1行按照如下格式給出植物pr, c的資訊:第乙個整數為score[pr, c], 第二個整數為集合attack[pr, c]中的位置個數w,接下來w個位置資訊(r』, c』),表示pr, c可以攻擊位置第r』 行第c』 列。

輸出格式:

輸出檔案pvz.out僅包含乙個整數,表示可以獲得的最大能源收入。注意,你也可以選擇不進行任何攻擊,這樣能源收入為0。

輸入樣例#1:

3 2

10 0

20 0

-10 0

-5 1 0 0

100 1 2 1

100 0

輸出樣例#1:

25

約20%的資料滿足1 ≤ n, m ≤ 5;

約40%的資料滿足1 ≤ n, m ≤ 10;

約100%的資料滿足1 ≤ n ≤ 20,1 ≤ m ≤ 30,-10000 ≤ score ≤ 10000

有點像一道拓撲排序刪環的題目——攝像頭,也像noip2015d1t2資訊傳遞,拓撲排序刪環之後,這題是最大權閉合子圖。刪點不說了。

最大權閉合子圖可以看這篇博文,就像太空旅行計畫那題,吃乙個正分的植物相當於做乙個實驗盈利,吃乙個負分的植物相當於花錢帶乙個儀器。要吃乙個植物,就要把保護它的都先吃掉,就相當於要做乙個實驗就要把所需的儀器全花錢買下。

#include#include

#include

#include

#include

intn,m;

int score[1000]=;

inline

int id(int x,int

y)struct

tppointp[

1000

];bool usable[1000]=;

void del(intu)}

ints,t;

struct

edgee[

3000000

];int head[1000]=,cnt=2

;void add(int u,int v,intf);

head[u]=cnt++;

e[cnt]=;

head[v]=cnt++;

}int dis[1000

];bool

bfs()

}return dis[t]!=0;}

int dfs(int u,int

f)

if(flow_sum==0) dis[u]=-1

;

return

flow_sum;

}int

dinic()

return

ans;

}int

main()

for(int i=1;i<=n;i++)}}

for(int i=1;i<=n*m;i++)

if(p[i].ru==0&&!usable[i]) del(i);

long

long sum=0

;

for(int i=1,num=n*m;i<=num;i++)

}sum-=dinic();

if(sum<0) printf("

0\n"

);

else printf("

%lld\n

",sum);

return0;

}

洛谷 P1565 牛宮

題目 牛宮 思路 咳咳,先放個提交記錄 嗯再來個mjy0724的思路 然後就沒我什麼事了 有這麼幾點需要注意的地方 1 vector一定不能作為引數傳進函式,會t到飛起,親測100 50 2 第一列數要單獨判斷 3 字首和的處理,i,j 的字段和大於0的條件是sum j sum i 1 而非sum ...

洛谷P1565 牛宮

ap 神牛準備給自己蓋一座很華麗的宮殿。於是,他看中了一塊n m 的矩形空地。空地中每個格仔都有自己的海拔高度。ap 想讓他的宮殿的平均海拔在海平面之上 假設 海平面的高度是0,平均數都會算吧?而且,ap 希望他的宮殿盡量大,能夠容納更 多的人來膜拜他。請問ap 的宮殿最後會有多大?輸入格式 第一行...

洛谷P1565牛宮

傳送門 題目點這裡 首先理解題目,就是要求給定矩陣中權值和不小於零的最大子矩陣,資料範圍200也還不算棘手,暴力n 4的演算法也可以水到50分。正解要用到單調棧配合二分和字首和,複雜度n 3logn,跑得也還算快。分析一下,首先用乙個陣列a i j 記錄下第 i 行前 j 個元素之和,然後開始乙個個...