预处理出来任意两点的距离,然后可以顺着trie树中的节点走,不能走到不合法的地方,另开一维表示走到了哪里,依次来更新。
注意判断一下起点是不是合法。
1 #include <iostream>
2 #include<cstdio>
3 #include<cstring>
4 #include<algorithm>
5 #include<stdlib.h>
6 #include<vector>
7 #include<cmath>
8 #include<queue>
9 #include<set>
10 using namespace std;
11 #define N 510
12 #define LL long long
13 const double eps = 1e-8;
14 const double pi = acos(-1.0);
15 const double INF = 1e21;
16 const int child_num = 51;
17 double w[55][55];
18 class AC
19 {
20 private:
21 int ch[N][child_num];
22 int fail[N];
23 int val[N];
24 int id[128];
25 int Q[N];
26 double dis[55][N];
27 int sz;
28 public:
29 void init()
30 {
31 fail[0] = 0;
32 for(int i = 0 ; i< child_num ; i++)
33 id[i] = i;
34 }
35 void reset()
36 {
37 memset(ch[0],0,sizeof(ch[0]));
38 memset(val,0,sizeof(val));
39 sz = 1;
40 }
41 void insert(int *a,int k,int key)
42 {
43 int i,p=0;
44 for(i = 1;i <= k; i++)
45 {
46 int d = a[i];
47 if(ch[p][d]==0)
48 {
49 memset(ch[sz],0,sizeof(ch[sz]));
50 ch[p][d]= sz++;
51 }
52 p = ch[p][d];
53 }
54 val[p] = key;
55 }
56 void construct()
57 {
58 int i,head= 0 ,tail = 0;
59 for(i = 1 ;i < child_num ; i++)
60 {
61 if(ch[0][i])
62 {
63 fail[ch[0][i]] = 0;
64 Q[tail++] = ch[0][i];
65 }
66 }
67 while(head!=tail)
68 {
69 int u = Q[head++];
70 val[u]|=val[fail[u]];
71 for(i = 1; i < child_num ; i++)
72 {
73 if(ch[u][i])
74 {
75 fail[ch[u][i]] = ch[fail[u]][i];
76 Q[tail++] = ch[u][i];
77 }
78 else ch[u][i] = ch[fail[u]][i];
79 }
80 }
81 }
82 void work(int n)
83 {
84 int i,j,g;
85 for(i = 1; i <= n ;i++)
86 for(j = 0 ; j <= sz ;j++)
87 dis[i][j] = INF;
88 if(val[1])
89 {
90 puts("Can not be reached!");
91 return ;
92 }
93 dis[1][ch[0][1]] = 0;
94 for(i = 1 ; i <= n ;i++)
95 {
96 for(j = 0; j < sz ;j++)
97 {
98 for(g = 1; g <= n ;g++)
99 {
100 int np = ch[j][g];
101 if(val[np]) continue;
102 dis[g][np] = min(dis[g][np],dis[i][j]+w[i][g]);
103 }
104 }
105 }
106 double ans = INF;
107 for(i = 0 ; i < sz ; i++)
108 {
109 ans = min(ans,dis[n][i]);
110 }
111 if(fabs(ans-INF)<eps) puts("Can not be reached!");
112 else
113 printf("%.2f\n",ans);
114 }
115 }ac;
116 struct node
117 {
118 double x,y;
119 }pp[55];
120 double cdis(node a,node b)
121 {
122 return sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y));
123 }
124 int a[10];
125 int main()
126 {
127 int n,m,k,i,j;
128 ac.init();
129 while(scanf("%d%d",&n,&m)&&n&&m)
130 {
131 ac.reset();
132 for(i = 1 ;i <= n; i++)
133 {
134 scanf("%lf%lf",&pp[i].x,&pp[i].y);
135 }
136 for(i = 1; i <= n ;i++)
137 for(j = 1; j <= n ;j++)
138 w[i][j] = cdis(pp[i],pp[j]);
139 for(i = 1; i <= m ; i++)
140 {
141 scanf("%d",&k);
142 for(j= 1 ;j <= k; j++)
143 scanf("%d",&a[j]);
144 ac.insert(a,k,1);
145 }
146 ac.construct();
147 ac.work(n);
148 }
149 return 0;
150 }
时间: 2024-11-09 02:04:59