トピックリンク:https://ac.nowcoder.com/acm/contest/1168/C
さらに少ない双方向側mよりの視点から構築された最も一般的なショート、ある、その書き込み以来多くが、レコードの最短どのように最短経路を知りません。録音は十分ではリラックスして、リラックスは、ポイントが繰り返しリラクゼーション、あなたは何回かその前身を更新することができたときに、それが最短経路上の点があるときに、たるみができないことを、各時点のたるみ前駆体だっ記録されていますそれは、最後に記録されたスラック前駆体です。
そして端から前駆、出力するアレイ中に存在する出力点を通る逆最短経路を横断します。
コードは以下の通りであります:
1の#include <ビット/ STDC ++ H> 2 の#define MEM(A、B)のmemset(A、B、はsizeof()) 3 CONST INT MAXN = 650 。 4 constの ダブル INF = 0x3f3f3f3f * 1.0 ; 5 使用して 名前空間はstdを、 6 7 INT N、K。 8 ダブルM、DIS [MAXN]。 9 int型ヘッド[MAXN]、CNT、VIS [MAXN]。 10 int型のプレ[MAXN]。 11 12 構造体ノード 13 { 14 ダブルX、Y、Z。 15 }ノード[MAXN]。 16 17 構造体のエッジ 18 { 19 INT 次へ。 20 二重W。 21 }エッジ[MAXN * MAXN]。 22 23 構造体N 24 { 25 のint ポット; 26の ダブルDIS; 27 ブール 演算子 <(CONST N&)CONST 28 { 29の リターン DIS> a.dis。 30 } 31 }なし。 32 33 空隙追加(int型、INT B、ダブルC) 34 { 35 CNT ++ 。 36 エッジ[CNT] .TO = B。 37 エッジ[CNT] .next = ヘッド[A]。 38 エッジ[CNT] .W = C。 39 頭[] = CNT。 40 } 41 42 空隙をDij() 43 { 44 PRIORITY_QUEUE <N> Q。 45 no.pot = 0、no.dis = 0 。 46 フィル(DIS、DIS + N + 2、INF)、MEM(VIS、0 ); 47の DIS [ 0 ] = 0 ; 48 Q.push(NO)。 49 N; 50 ながら(!Q.empty()) 51 { 52 A = Q.top()。 53 Q.pop()。 54 であれば(VIS [a.pot]) 55を 続けます。 56 VIS [a.pot] = 1 。 57 のために(INTは iはヘッド[a.pot] =; I =! - 1 ; iが= エッジを[I] .next) 58 { 59 60 INTへ= エッジ[I] .TO; 61れる IF(DIS [に対する]> DIS [a.pot] + エッジ[I] .W) 62であり 、{ 63である DIS [に対する] DIS = [a.pot] + エッジ[I] .W; 64 no.pot = no.dis =にDIS [へ]; 65 前= a.pot [へ]; // 緩和レコードが更新され、それは最小限に最後に記録され、いくつかのたるみを更新経路上の 66 Q.push(NO); 67 } 68 } 69 } 70 } 71は、 72 のint main()の 73 { 74 MEM(ヘッド、 - 1)、CNT = 0 。 75 のscanf(" %D%LF "、&N、&M)。 76 のscanf(" %LF%LF%LF%LF%LF%LF "、およびノード[ 0 ] .X、およびノード[ 0 ]・Y、およびノード[ 0 ] .Z、およびノード[N + 1 ] .X、&ノード[ N + 1 ] .Y、およびノード[N + 1 ] .Z)。// 起点终点 77 のために(INT iが= 1 ; iが<= N; I ++ ) 78 のscanfを("%LF%LF%LF 」、およびノード[i]は.X、およびノード[I] .Y、およびノード[I] .Z); 79 用(INTは私= 0 ; I <N + 1 ; I ++ ) 80 { 81 のための(int型 J = I + 1、J <= N + 1 J ++; ) 82 { 83 二重 *(ノード[I] - JL =(ノード[J] .Xノード[I] .X)。 X -ノード[J] .X)+(ノード[I] .Y -ノード[J] .Y)*(ノード[I] .Y -ノード[J] .Y)+(ノード[I] .Z -ノード[J] .Z)*(ノード[i]が.Z - ノード[J] .Z)、 84 であれば(JL <= M * M) 85 { 86 アドオン(I、J、SQRT(JL)); 87 アドオン(J、I、SQRT(JL)); 88 } 89 } 90 } 91 をDij()。 92 であれば(DIS [N + 1 ] = INF *!1.0 ) 93 { 94 のprintf(" %.3lf \ n "、DIS [N + 1 ])。 95 のprintf(" スタート" ); 96 INT P、LEN = 0 、ANS [MAXN]。 97 、P = N + 1; // 端 98 ながら(P =!0)// 開始点に等しいされていない 99 { 100 ANS [LEN ++] = ; P 101 P = [P]事前; 102 } 103 のために(INT I = LEN 。1 ; I> 0 ; i-- ) 104 のprintf(" %のD " 、ANS [I]); 105 のprintf(" エンド\ N- " ); 106 } 107 そう 108 printf(" -1 \ N " ); 109 戻り 0 ; 110 }