02_嵌套矩形(DAG最长路问题)

来源:刘汝佳《算法竞赛入门经典--训练指南》 P60 问题2:

问题描述:有n个矩形,每个矩形可以用两个整数a,b描述,表示它们的长和宽。矩形X(a,b)可以嵌套在矩形Y(c,d)中的条件为:当且仅当a<c,b<d 或者b<c,a<d(相当于把矩形X旋转90  度)。选出尽量多的矩形排成一行,使得除了最后一个之外,每一个矩形都可以嵌套在下一个矩形内。

分析:对于本题中的n个矩形,以每个矩形作为一个点,若X矩形能嵌套在Y矩形中,则从X向Y连一条边,题目则变为了在DAG(无回路有向图)中求最长路径的问题。对每一个矩形i,设d(i)为矩形i结尾的最长链的长度,则d(i)=Max{0,d(j)|(矩形j可以嵌套在矩形i中)}+1;

例题来源:http://acm.nyist.net/JudgeOnline/problem.php?pid=16

代码实现:

 1 #include "stdio.h"
 2 #include "string.h"
 3 #define N 1005
 4 
 5 int n;
 6 int dp[N];
 7 int map[N][N];
 8 
 9 struct point
10 {
11     int x,y;
12 }a[N];
13 
14 int inline Max(int a,int b){ return a>b?a:b; }
15 
16 int Pudge(int a,int b,int c,int d)
17 {
18     if( (a<c&&b<d) || (b<c&&a<d) )
19         return 1;
20     return 0;
21 }
22 
23 int DFS(int k)
24 {
25     if(dp[k]!=-1)
26         return dp[k];
27     int i;
28     dp[k] = 1;
29     for(i=0; i<n; i++)
30     {
31         if(map[i][k]==1)
32             dp[k] = Max(dp[k],DFS(i)+1);
33     }
34     return dp[k];
35 }
36 
37 int main()
38 {
39     int T;
40     int i,j;
41     int ans;
42     scanf("%d",&T);
43     while(T--)
44     {
45         ans = 0;
46         scanf("%d",&n);
47         for(i=0; i<n; i++)
48             scanf("%d %d",&a[i].x,&a[i].y);
49         memset(map,0,sizeof(map));
50         for(i=0; i<n; i++)
51         {
52             for(j=0; j<n; j++)
53             {
54                 if(i==j) continue;
55                 if(Pudge(a[i].x,a[i].y,a[j].x,a[j].y))
56                     map[i][j] = 1;
57             }
58         }
59         memset(dp,-1,sizeof(dp));
60         for(i=0; i<n; i++)
61             ans = Max(ans,DFS(i));
62         printf("%d
",ans);
63     }
64     return 0;
65 }
66         
原文地址:https://www.cnblogs.com/ruo-yu/p/4383521.html