6.6模拟题 维修店(1791)

题目

   A公司想在N个城市中选择M个来开维修店,而购买了A公司产品的人如果要维修,可以送到最近的维修店。A公司想知道,选择哪些城市开维修店可以使得离维修店最远的那个城市离维修店的距离尽量小。给出N个城市的坐标(城市的坐标是唯一的),你能帮A公司求出这个最小的距离吗?

Input

   输入的第一行包含两个整数,分别是城市数N以及维修店数M。 
   接下来的N行各包含两个数,分别是每个城市的X坐标和Y坐标。 

Output

   输出只有一行,包含一个小数,为所求的最小距离,保留2位有效数字。

Sample Input

4 2
0 0
1 1
2 4
3 9

Sample Output

3.16

对于所有的数据,1 ≤ M ≤ N ≤ 20,-1000 ≤ X,Y ≤ 1000。

题解

从数据(1 ≤ M ≤ N ≤ 20)大小可以看出,题目可以用搜索完成。
因为要在n个城市中选择m个开维修店,所以应该是要求从n个数中选m个的组合,在每个组合再求距离。

组合的求法
dep表示选了dep个数,pre表示在n个数中选到第pre个数。
当dep>m时,就求最大值(注意选中的点不能算进去)并和答案比较,退出
这时就可以用选中的点i(a[i,j])来更新d[j](注意选中的点不能算进去),可以用回溯来改变v值

代码

var
  n,m,i,j:longint;
  ans:real;
  t:array[1..20,1..2]of longint;
  a:array[1..20,1..20]of real;
  v:array[1..20]of boolean;
  d:array[1..20]of real;

procedure sea(pre,dep:longint);
var
  t:array[1..20]of real;
  i,j:longint;
  ts:real;
begin
  if dep>m then
    begin
      ts:=0;
      for i:=1 to n do
        if (not v[i]) and (d[i]>ts) then ts:=d[i];
      if ts<ans then ans:=ts;
      exit;
    end;
  for i:=pre+1 to n-(m-dep) do
    begin
      t:=d;
      v[i]:=true;
      for j:=1 to n do
        if (not v[j]) and (a[i,j]<d[j]) then d[j]:=a[i,j];
      sea(i,dep+1);
      v[i]:=false;
      d:=t;
    end;
end;

begin
  assign(input,'repair.in');
  assign(output,'repair.out');
  reset(input);rewrite(output);
  readln(n,m);
  for i:=1 to n do
    readln(t[i,1],t[i,2]);
  for i:=1 to n do
    for j:=1 to n do
      if i<>j then a[i,j]:=sqrt(sqr(t[i,1]-t[j,1])+sqr(t[i,2]-t[j,2]))
              else a[i,j]:=maxint;
  ans:=maxint;
  for i:=1 to n do
    d[i]:=maxint;
  sea(0,1);
  writeln(ans:0:2);
  close(input);close(output);
end.
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值