終於把這個系列刷完了,雖然還有幾道題沒有搞定,但是在建模上已經有了長足的進步。
這道題的建模和之前的方格取數有點像,同樣先將棋盤染色。
1.源點向白色塊連線一條邊,容量為1,黑色塊向匯點連線一條邊,容量為1.
2.對於所有的白塊,向它能走到的地方連一條邊,容量為1
然後求乙個最大流,又可以走的點減去最大流的值,其實要求最小割。
#include
#include
#include
#include
#include
#include
using
namespace
std;
const
int maxn = 200010;//點數的最大值
const
int maxm = 500010;//邊數的最大值
const
int inf = 0x3f3f3f3f;
struct edge
edge[maxm]; //注意是maxm
int tol;
int head[maxn];
int gap[maxn],dep[maxn],cur[maxn];
void init()
void addedge(int u,int v,int w,int rw = 0)
int q[maxn];
void bfs(int start,int end)
}}int s[maxn];
int sap(int start,int end,int n)
for(int i = 0; i < top; i++)
ans += min;
top = inser;
u = edge[s[top]^1].to;
continue;
}bool flag = false;
int v;
for(int i = cur[u]; i != -1; i = edge[i].next)
}if(flag)
int min = n;
for(int i = head[u]; i != -1; i = edge[i].next)
if(edge[i].cap - edge[i].flow && dep[edge[i].to] < min)
gap[dep[u]]--;
if(!gap[dep[u]])
return ans;
dep[u] = min + 1;
gap[dep[u]]++;
if(u != start)
u = edge[s[--top]^1].to;
}return ans;
}void print_all()
}int dx = ;
int dy = ;
int id[201][201];
int c[201][201];
int block[201][201];
int main()
init();
int b = 1,w = (n *n +1)/2+1;
for(int i = 1;i<=n;i++)
else}}
for(int i = 1;i<=n;i++)
addedge(0,id[i][j],1);
}else}}
int ans = sap(0,w,w+1);
printf("%d\n",n*n - m-ans);
return
0;}
網路流二十四題
開始了我的網路流 24 題之旅,寫在一起到時候方便一起複習哦。其實這並不是真的二十四題,有一些過於水的我就不寫上來了。然後有的 太水了就不寫了。感覺這些題目還是比較基礎的,方法卻值得借鑑!剩餘題目 航空路線問題 火星探險問題以下 題目描述 點此看題 解法 你發現時間是最大的障礙,因為對於不同的時間飛...
網路流二十四題之航空路線問題
這道題的建模很有意思 1.首先每個點,除了起點,都向拆點後的點練一天容量1,費用 1的邊,代表只能走一次,負費用是為了求最大的費用,也就是最多的經過點。對於起點,容量變成2,費用不變。2.其次對於一天航線,終點在拆點後的點集向起點連一條邊,容量無限,費用為0,代表兩個城市可以達到。之後一次費用流,如...
網路流二十四題之數字梯形問題
這道題的建模過程需要按照三個要求分開建模 規則一 每條路徑不相交 因為每條路徑不相交,所以每個每個節點只能經過一次。所以我們拆點x,y,順便將每個點都標號 1.源點向第一層的x集合連一條邊,費用為0,容量為1.最後一層的y集合向匯點連一條邊,容量為1,費用為0 2.x集合中的每乙個點xi,向y集合中...