我就是脑子被驴踢了之前才做不出来的。。呵呵哒
因为要求转换的最少,所以如果两个路由器之间能架构网络,那么距离就是1,然后如果之间可以建立网络但是k的个数超了也是不可以纳入更新的。
#include <cstdio>
#include <cstring>
#include <iostream>
#include <queue>
#include <cmath>
#include <cstdlib>
using namespace std;
#define maxn 220
#define ll long long
int dis[maxn][maxn],vis[maxn],num[maxn],ans[maxn];
int n,m,k;
ll r;
class node
{
public:
int x,y,flag;
}a[maxn];
queue<int>que;
void spfa()
{
//debug
//
for(int i=1;i<=n+m;i++)
{
ans[i]=-1;
}
ans[1]=0;
que.push(1);
vis[1]=1;
while(!que.empty())
{
int x=que.front();
que.pop();
vis[x]=0;
//printf("%d dis=%d num=%d\n",x,ans[x],num[x]);
for(int i=1;i<=n+m;i++)
{
if(dis[x][i]!=-1)
{
if(ans[i]==-1||ans[x]+dis[x][i]<ans[i])
{
if(a[i].flag==2)
{
if(num[x]+1>k) continue;
num[i]=num[x]+1;
}
else num[i]=num[x];
ans[i]=ans[x]+dis[x][i];
//if(!vis[i]) printf("pre=%d child=%d dis=%d d=%d\n",x,i,ans[i],num[i]);
if(!vis[i])
que.push(i),vis[i]=1;
}
else if(ans[i]!=-1&&ans[x]+dis[x][i]==ans[i]&&num[x]+1<num[i])
{
num[i]=num[x]+1;
if(!vis[i]) que.push(i),vis[i]=1;
}
}
}
}
cout<<ans[2]-1<<endl;
}
void init()
{
for(int i=0;i<maxn;i++)
{
vis[i]=num[i]=0;
for(int j=0;j<maxn;j++)
dis[i][j]=-1;
}
}
int main()
{
while(cin>>n>>m>>k>>r)
{
init();
for(int i=1;i<=n;i++)
{
cin>>a[i].x>>a[i].y;
a[i].flag=1; // 1--> fixed
}
for(int i=n+1;i<=n+m;i++)
{
cin>>a[i].x>>a[i].y;
a[i].flag=2; //2--> choose
}
for(int i=1;i<=n+m;i++)
{
for(int j=1;j<=n+m;j++)
{
if(i==j){
dis[i][j]=0;continue;
}
ll diss=(ll)(a[i].x-a[j].x)*(ll)(a[i].x-a[j].x)+(ll)(a[i].y-a[j].y)*(ll)(a[i].y-a[j].y);
if(diss<=r*r)
{
dis[i][j]=1;
dis[j][i]=1;
}
}
}
spfa();
}
return 0;
}