POJ-3020 Antenna Placement

Posted on 2021-12-01 21:01  Capterlliar  阅读(17)  评论(0编辑  收藏  举报

题意:给定一张图,上面有很多*。有一些1*2的小纸片,问至少用多少小纸片能覆盖所有的*。

解:翻译一下:每个*看作一个点,两个*之间可以有一条边。问至少选择多少边,能够覆盖所有点。也就是求最小路径覆盖。

二分图最小路径覆盖=所有点个数-最大匹配。

这里很把所有*染色有点麻烦,不如拆点,把所有点拆成一入一出,分成两边,最后除以2。

交了好几发RE,最后怒把数组改成500,过了。poj老爷机名不虚传()

代码:

 1 #include<stdio.h>
 2 #include <algorithm>
 3 #include <string.h>
 4 #include <queue>
 5 #include <vector>
 6 #include <iostream>
 7 using namespace std;
 8 #define ll long long
 9 #define maxx 505
10 #define inf 0x3f
11 const int mod=1e9+7;
12 //#define int long long
13 vector<int> e[maxx];
14 int n,m;
15 int num;
16 int vis[maxx]={0},match[maxx]={0};
17 int mp[maxx][maxx];
18 int xx[4]={0,1,0,-1};
19 int yy[4]={1,0,-1,0};
20 int dfs(int now){
21     for(int i=0;i<e[now].size();i++){
22         int to=e[now][i];
23         if(!vis[to]){
24             vis[to]=1;
25             if(!match[to]||dfs(match[to])){
26                 match[to]=now;
27                 return 1;
28             }
29         }
30     }
31     return 0;
32 }
33 signed main() {
34     int T;
35     cin>>T;
36     char s[maxx];
37     while(T--){
38         num=0;
39         memset(mp,0,sizeof mp);
40         memset(match,0,sizeof match);
41         for(int i=0;i<maxx;i++)
42             e[i].clear();
43         cin>>n>>m;
44         for(int i=0;i<n;i++) {
45             cin>>s;
46             for (int j = 0; j < m; j++)
47                 mp[i][j]=s[j]=='*'?++num:0;
48         }
49         for(int i=0;i<n;i++)
50             for(int j=0;j<m;j++){
51                 if(mp[i][j]>0){
52                     for(int k=0;k<4;k++){
53                         int tx=i+xx[k],ty=j+yy[k];
54                         if(tx<0||tx>=n||ty<0||ty>=m)
55                             continue;
56                         if(mp[tx][ty]>0)
57                             e[mp[i][j]].push_back(mp[tx][ty]);
58                     }
59                 }
60             }
61         int ans=0;
62         for(int i=1;i<=num;i++) {
63             memset(vis,0,sizeof vis);
64             if (dfs(i))
65                 ans++;
66         }
67         cout<<num-ans/2<<endl;
68     }
69     return 0;
70 }
View Code