博客园  :: 首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

tyvj p1222微子危机——聚焦(生成树)

Posted on 2010-10-21 08:29  深处的心扉  阅读(392)  评论(0)    收藏  举报

背景 Background
№.4
Guiolk联盟以迅雷不及掩耳之势向Summer发起异常猛烈的进攻!多亏Summer在这之前已经准备好备战资源,并完成了战略转移,否则后果不堪设想。可终究微子的能量太强大了,Summer军团损失惨重。与此同时,Summer的科学家们也在加紧研究破解微子的方法,以拯救受伤的人们!终于,他们发现了……于是,全军团奋起反击……

 


描述 Description
科学家发现微子束是有许多微子组成的。当很多微子被联通的时候,它们就会发出极其强大的力量。于是我们的任务就是把它拆散。最好的攻击就是S射线的攻击(因为它速度快,而且有解除连通的力量),我们已请求Winter的光援助。
S射线能击破微子。当一束S射线射到一个微子上时,这个微子就会被击破,而且S射线还可以任意折射到其他微子上。假设我们能用最短的S射线去击破所有的微子,那么从发射到全部击破所有微子时,需要多长的S射线呢?这关系到节省核能的问题,因为S射线是非常耗能的。
一个微子束存在于一个三维空间中,每个微子都有一个不重复的坐标。射线从点(-1,-1,-1)发射,求所需最短的S射线。
(*注:意思是要让总的S射线最短。*)


输入格式 Input Format
有若干行,每一行有三个数,表示一个微子的坐标,用空格隔开。微子束所在的三维空间是一个正方体,从(0,0,0)到(1*10^6,1*10^6,1*10^6)。


输出格式 Output Format
只有一行,就是所需的最短的S射线(从射线开始发射到微子全部击破为止),保留4位小数。


样例输入 Sample Input

2 3 11
3 2 11
2 3 12
样例输出 Sample Output

15.4142


时间限制 Time Limitation
因为有太多的微子束,所以对于每一个微子束,你只有1s的时间。


注释 Hint
对于100%的数据,最多不超过1000个微子。

 

 

分析:从题目很容易就看出是最小生成树问题,可用prim,kruskal算法

 

prim算法:

代码
1 program p1222;
2 var
3 n:longint; ans:real;
4 dist:array[1..1001]of real;
5 map:array[1..1001,1..1001]of real;
6 x,y,z:array[1..1001]of real;
7 f:array[1..1001]of boolean;
8
9 procedure init;
10 var i,j:integer;
11 begin
12 fillchar(f,sizeof(f),true);
13 n:=1;
14 x[1]:=-1;
15 y[1]:=-1;
16 z[1]:=-1;
17 while not eof do
18 begin
19 inc(n);
20 readln(x[n],y[n],z[n]);
21 end;
22 for i:=1 to n do
23 for j:=1 to n do
24 begin
25 map[i,j]:=sqrt(sqr(x[i]-x[j])+sqr(y[i]-y[j])+sqr(z[i]-z[j]));
26 if map[i,j]=0 then
27 map[i,j]:=maxlongint;
28 end;
29 f[1]:=false;
30 for i:=1 to n do
31 dist[i]:=map[1,i];
32 end;
33
34 procedure prim;
35 var i,j,k:longint;min:real;
36 begin
37 for i:=1 to n-1 do
38 begin
39 min:=maxlongint;
40 k:=0;
41 for j:=1 to n do
42 if (dist[j]<min)and(f[j]) then
43 begin
44 min:=dist[j];
45 k:=j;
46 end;
47 if k<>0 then
48 begin
49 ans:=ans+min;
50 f[k]:=false;
51 end;
52 for j:=1 to n do
53 if (map[k,j]<dist[j])and(f[j])then
54 dist[j]:=map[k,j];
55 end;
56 end;
57
58 begin
59 init;
60 prim;
61 writeln(ans:0:4);
62 end.