# BZOJ1097 [POI2007]旅游景点atr

  1 /**************************************************************
2     Problem: 1097
3     User: rausen
4     Language: C++
5     Result: Accepted
6     Time:18456 ms
7     Memory:98872 kb
8 ****************************************************************/
9
10 #include <cstdio>
11 #include <cstring>
12 #include <algorithm>
13 #include <queue>
14
15 using namespace std;
16 const int N = 2e4 + 5;
17 const int M = 2e5 + 5;
18 const int K = 22;
19 const int Tot_S = 1 << 20;
20 const int inf = 1e9;
21
22 struct edge {
23     int next, to, v;
24     edge(int _n = 0, int _t = 0, int _v = 0) : next(_n), to(_t), v(_v) {}
25 } e[M << 1];
26
27 struct heap_node {
28     int v, to;
29     heap_node(int _v = 0, int _t = 0) : v(_v), to(_t) {}
30
31     inline bool operator < (const heap_node &p) const {
32         return v > p.v;
33     }
34 };
35
36 int n, m, k, ans;
37 int first[N], tot;
38 int bin[K], a[K];
39 int dis[K][K], d[N];
40 int S, S1;
41 int f[Tot_S][K];
42 priority_queue <heap_node> h;
43
45     static int x;
46     static char ch;
47     x = 0, ch = getchar();
48     while (ch < '0' || '9' < ch)
49         ch = getchar();
50     while ('0' <= ch && ch <= '9') {
51         x = x * 10 + ch - '0';
52         ch = getchar();
53     }
54     return x;
55 }
56
57 inline void Add_Edges(int x, int y, int z) {
58     e[++tot] = edge(first[x], y, z), first[x] = tot;
59     e[++tot] = edge(first[y], x, z), first[y] = tot;
60 }
61
62 inline void add_to_heap(int p) {
63     static int x;
64     for (x = first[p]; x; x = e[x].next)
65         if (d[e[x].to] == -1)
66             h.push(heap_node(e[x].v + d[p], e[x].to));
67 }
68
69 void Dijkstra(int S) {
70     static int p;
71     memset(d, -1, sizeof(d));
72     while (!h.empty()) h.pop();
74     while (!h.empty()) {
75         if (d[h.top().to] != -1) {
76             h.pop();
77             continue;
78         }
79         p = h.top().to;
80         d[p] = h.top().v;
81         h.pop();
83     }
84 }
85
86 int main() {
87     int i, j, x, y, z;
89     for (i = 1; i <= m; ++i) {
92     }
93     for (i = 1; i <= k + 1; ++i) {
94         Dijkstra(i);
95         for (dis[i][0] = d[n], j = 1; j <= k + 1; ++j)
96             dis[i][j] = d[j];
97     }
98     for (i = bin[0] = 1; i <= k + 1; ++i) bin[i] = bin[i - 1] << 1;
99     for (x = read(), i = 1; i <= x; ++i)
100         y = read(), z = read(), a[z] += bin[y - 2];
101
102     memset(f, 0x3f, sizeof(f));
103     for (S = f[0][1] = 0; S < bin[k]; ++S)
104         for (i = 1; i <= k + 1; ++i) if (f[S][i] != 0x3f3f3f3f)
105             for (j = 2; j <= k + 1; ++j) {
106                 S1 = S | bin[j - 2];
107                 if ((S & a[j]) == a[j]) f[S1][j] = min(f[S1][j], f[S][i] + dis[i][j]);
108             }
109     for (ans = inf, i = 1; i <= k + 1; ++i)
110         ans = min(ans, f[bin[k] - 1][i] + dis[i][0]);
111     printf("%d\n", ans);
112     return 0;
113 }
View Code

posted on 2015-04-14 22:45  Xs酱~  阅读(421)  评论(0编辑  收藏  举报