DAG上的动态规划,需要注意最后要打印起点到终点的一条路,因此状态d[i]定义为从 i 出发的最长路的距离。
UVa今天这是怎么了,两道题都是将近5min才出结果。
1 # include <stdio.h>
2 # include <string.h>
3 # include <stdlib.h>
4
5 # define MAXD 11
6 # define MAXN 31
7
8 int k, n;
9 int d[MAXN];
10 int box[MAXN][MAXD];
11 int g[MAXN][MAXN];
12
13 int cmp(const void *x, const void *y)
14 {
15 return (*(int *)x) - (*(int *)y);
16 }
17
18 int dp(int i);
19 void print_order(int i);
20
21 int main()
22 {
23 int i, j, p, fit, max, tm, mi;
24
25 while (~scanf("%d%d", &k, &n))
26 {
27 for (i = 1; i <= k; ++i)
28 {
29 for (j = 0; j < n; ++j)
30 scanf("%d", &box[i][j]);
31 qsort(box[i], n, sizeof(int), cmp);
32 }
33
34 memset(g, 0, sizeof(g));
35 memset(d, 0, sizeof(d));
36
37 for (i = 1; i <= k; ++i)
38 for (j = 1; j <= k; ++j)
39 {
40 fit = 1;
41 for (p = 0; p < n; ++p)
42 if (box[i][p] <= box[j][p])
43 {
44 fit = 0;
45 break;
46 }
47 if (fit) g[i][j] = 1;
48 }
49
50 max = 0;
51 for (i = 1; i <= k; ++i)
52 if ((tm = dp(i)) > max)
53 {
54 max = tm;
55 mi = i;
56 }
57
58 printf("%d\n", max);
59 print_order(mi);
60 printf("\n");
61 }
62
63 return 0;
64 }
65
66 int dp(int i)
67 {
68 int j, t;
69 if (d[i] > 0) return d[i];
70 d[i] = 1;
71 for (j = 1; j <= k; ++j)
72 if (g[j][i])
73 {
74 t = dp(j) + 1;
75 if (d[i] < t) d[i] = t;
76 }
77 return d[i];
78 }
79
80 void print_order(int i)
81 {
82 int j;
83 printf("%d ", i);
84 for (j = 1; j <= k; ++j)
85 if (g[j][i] && d[i] == d[j]+1)
86 {
87 print_order(j);
88 break;
89 }
90 }