2668 cqoi2012 交換棋子

2021-07-27 08:30:22 字數 2395 閱讀 5745

time limit: 3 sec  

memory limit: 128 mb

submit: 1136  

solved: 423 [

submit][

status][

discuss]

有乙個n行m列的黑白棋盤,你每次可以交換兩個相鄰格仔(相鄰是指有公共邊或公共頂點)中的棋子,最終達到目標狀態。要求第i行第j列的格仔只能參與mi,j

次交換。

第一行包含兩個整數n,m(1<=n, m

<=20)。以下n行為初始狀態,每行為乙個包含m個字元的01串,其中0表示黑色棋子,1表示白色棋子。以下n行為目標狀態,格式同初始狀態。以下n行每行為乙個包含m個0~9數字的字串,表示每個格仔參與交換的次數上限。

輸出僅一行,為最小交換總次數。如果無解,輸出-1。

3 3110000

001000

110100

222222

2224 [

submit][

status][

discuss]

資料範圍非常網路流,答案非常費用流,不過不會建模。。

忽略圖中的白色棋子,只考慮黑色棋子,問題轉變成

將原圖中的每個黑色棋子移動成新圖的樣子,最少需要移動多少步

約束是每個格仔有乙個經過次數的上限

把某個黑棋子,從格仔a移動到格仔b,視作從a流出流入b

那麼就將乙個點i拆成三個點,xi,yi,zi,連(xi,yi)和(yi,zi)兩條邊

前者用來限制流入後者限制流出

分類討論圖中的每個點(i,j),記a = (xi,yi)的容量,b = (yi,zi)的容量,交換上限為wi,j

如果原圖和新圖中某個位置顏色相同,說明其流入流出次數應該相等,所以a = b = wi,j / 2

如果原圖是黑色而新圖是白色,說明應該多流出一次,所以a = wi,j / 2,b = (wi,j + 1) / 2

反之,同理可得a = (wi,j + 1) / 2,b = wi,j / 2

上述除法全部是取下整

構建超級源s,超級匯t

如果某點在原圖是黑色,連s到yi,j容量為1的邊,代表這個黑棋子從這個點出發

如果某點在新圖是黑色,連yi,j到t容量為1的邊,代表必須有乙個黑棋子在這裡停止

最後,根據八連通把x,z之間的邊建完,跑個最小費用最大流就行了

#include#include#include#include#includeusing namespace std;

const int maxn = 1222;

const int maxm = 4e5 + 40;

const int inf = 1e9 + 233;

const int dx[8] = ;

const int dy[8] = ;

struct e

e(int to,int cap,int flow,int cost):

to(to),cap(cap),flow(flow),cost(cost){}

}edgs[maxm];

int n,m,s,t,tot,t1,t2,cnt,num[22][22],a[22][22],b[22][22],cost[maxn],flow[maxn],from[maxn];

char ch[22],s[22][22],t[22][22];

bool vis[maxn];

vector v[maxn];

queue q;

void add(int x,int y,int cap,int cost)

bool spfa()

}return cost[t] != inf;}

int main()

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

if (t1 != t2)

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

int maxflow,cost; maxflow = cost = 0;

while (spfa())

}cout << (maxflow == t1 ? cost : -1) << endl;

return 0;

}

BZOJ 2668 cqoi2012 交換棋子

time limit 3 sec memory limit 128 mb submit 1112 solved 409 submit status discuss 有乙個n行m列的黑白棋盤,你每次可以交換兩個相鄰格仔 相鄰是指有公共邊或公共頂點 中的棋子,最終達到目標狀態。要求第i行第j列的格仔只能...

BZOJ2668 cqoi2012 交換棋子

題解 可以戳這裡 其實自己yy一下就知道這樣建圖的正確性了。感覺太神奇,居然還能拆成3個點 orzzzzzzzzzzzzzzzzzzzzzzzzz 跪跪跪跪跪跪跪跪 1 include2 3 include4 5 include6 7 include8 9 include10 11 include1...

bzoj2668 cqoi2012 交換棋子

description 有乙個 n 行 m 列的黑白棋盤,你每次可以交換兩個相鄰格仔 相鄰是指有公共邊或公共頂點 中的棋子,最終達到目標狀態。要求第 i 行第 j 列的格仔只能參與 m 次交換。input 第一行包含兩個整數 n,m 1 le n,m le 20 以下 n 行為初始狀態,每行為乙個包...