hdu 4462 第37届ACM/ICPC 杭州赛区 J题

题意:有一块n*n的田,田上有一些点可以放置稻草人,再给出一些稻草人,每个稻草人有其覆盖的距离ri,距离为曼哈顿距离,求要覆盖到所有的格子最少需要放置几个稻草人

由于稻草人数量很少,所以状态压缩枚举,之后慢慢判断即可,注意放稻草人的格子是不需要覆盖的

 1 #include<cstdio>
 2 #include<iostream>
 3 #include<algorithm>
 4 #include<cstring>
 5 #include<cmath>
 6 #include<queue>
 7 #include<map>
 8 using namespace std;
 9 #define MOD 1000000007
10 const int INF=0x3f3f3f3f;
11 const double eps=1e-5;
12 #define cl(a) memset(a,0,sizeof(a))
13 #define ts printf("*****
");
14 const int MAXN=1005;
15 int n,m,tt;
16 int x[MAXN],y[MAXN],r[MAXN],a[MAXN];
17 int main()
18 {
19     int i,j,k;
20     #ifndef ONLINE_JUDGE
21     freopen("1.in","r",stdin);
22     #endif
23     while(scanf("%d",&n)!=EOF)
24     {
25         if(n==0)    break;
26         scanf("%d",&k);
27         for(i=0;i<k;i++)    scanf("%d%d",&x[i],&y[i]);
28         for(i=0;i<k;i++)    scanf("%d",&r[i]);
29         int bit=(1<<k)-1;
30         int ans=1000000;
31         for(int s=0;s<=bit;s++)
32         {
33             int num=0;
34             for(j=0;j<k;j++)
35             {
36                 if(s&(1<<j))
37                 {
38                     a[num++]=j; //记录有放稻草人的格子
39                 }
40             }
41             bool vis[MAXN][MAXN],flag=1;
42             cl(vis);
43             for(i=1;i<=n;i++)
44             {
45                 for(j=1;j<=n;j++)
46                 {
47                     for(int d=0;d<k;d++)    //没放稻草人的格子
48                     {
49                         if(i==x[d]&&j==y[d])    vis[i][j]=1;
50                     }
51                     for(int d=0;d<num;d++)
52                     {
53                         if(fabs(i-x[a[d]])+fabs(j-y[a[d]])<=r[a[d]])    //曼哈顿距离
54                         {
55                             vis[i][j]=1;
56                             break;
57                         }
58                     }
59                     if(vis[i][j]==0)  //说明所有稻草人没法覆盖,该状态方案不可行
60                         flag=0;
61                 }
62                 if(flag==0) break;  //说明所有稻草人没法覆盖,该状态方案不可行
63             }
64             if(!flag)continue;
65             ans=min(ans,num);
66         }
67         if(ans>100000)ans=-1;
68         printf("%d
",ans);
69     }
70 }
原文地址:https://www.cnblogs.com/cnblogs321114287/p/4439492.html