ZOJ3519-Beautiful People:最长上升子序列的变形

Beautiful People

Special JudgeTime Limit: 10000/5000MS (Java/Others)Memory Limit: 128000/64000KB (Java/Others)

SubmitStatisticNext Problem

Problem Description

The most prestigious sports club in one city has exactly N members. Each of its members is strong and beautiful. More precisely, i-th member of this club (members being numbered by the time they entered the club) has strength Si and beauty Bi. Since this is a very prestigious club, its members are very rich and therefore extraordinary people, so they often extremely hate each other. Strictly speaking, i-th member of the club Mr X hates j-th member of the club Mr Y if Si <= Sj and Bi >= Bj or if Si >= Sj and Bi <= Bj (if both properties of Mr X are greater then corresponding properties of Mr Y, he doesn‘t even notice him, on the other hand, if both of his properties are less, he respects Mr Y very much).

To celebrate a new 2003 year, the administration of the club is planning to organize a party. However they are afraid that if two people who hate each other would simultaneouly attend the party, after a drink or two they would start a fight. So no two people who hate each other should be invited. On the other hand, to keep the club prestige at the apropriate level, administration wants to invite as many people as possible.

Being the only one among administration who is not afraid of touching a computer, you are to write a program which would find out whom to invite to the party.

Input

The first line of the input file contains integer N — the number of members of the club. (2 ≤ N ≤ 100 000). Next N lines contain two numbers each — Si and Brespectively (1 ≤ Si, Bi ≤ 109).

Output

On the first line of the output file print the maximum number of the people that can be invited to the party. On the second line output N integers — numbers of members to be invited in arbitrary order. If several solutions exist, output any one.

Sample Input

4
1 1
1 2
2 1
2 2

Sample Output

2
1 4

Source

Andrew Stankevich Contest 1

算法:最长上升子序列nlogn的解法(详情可以参见大白书P62),本题有一个不同的地方是,2个值都是严格递增(设为x,y),所以可根据x的值从小到大排序,这时我们从左往右只需考虑y的值因为x的值一定是递增的; 当x相同时根据y的值从大到小排序,为什么y要递减呢?因为当x相等时如果y为递增的话,那么选出的方案中就会将x相等的几个people都包含进去,显然是错的。然后我们就可以进行DP了,cnt[i]表示以第i个people结尾的最长上升子序列的长度,d[i]表示最长上升子序列长度为i时子序列末尾的最小y值(详见代码)。

本题还需要输出其中一种方案,我们只需根据DP得到的状态回溯输出就OK了。

 1 #include <iostream>
 2 #include <memory.h>
 3 #include <algorithm>
 4 #include <stdio.h>
 5 using namespace std;
 6 #define INF 1000000000
 7 #define MAXN 100010
 8 class CT
 9 {
10 public:
11     int x,y,num;
12     bool operator <(const CT &c2)const
13     {
14         if(x!=c2.x)
15             return x<c2.x;
16         return y>c2.y;
17     }
18 };
19
20 CT a[MAXN];
21 int d[MAXN];
22 int cnt[MAXN]={0};
23 int fa[MAXN];
24
25 int main()
26 {
27     #ifndef ONLINE_JUDGE
28     freopen("in.txt","r",stdin);
29     #endif
30     int n;
31     while(~scanf("%d",&n))
32     {
33         for(int i=1;i<=n;i++)
34         {
35             scanf("%d %d",&a[i].x,&a[i].y);
36             a[i].num=i;
37         }
38         sort(a+1,a+1+n);
39
40         d[0]=0;
41         fill_n(d+1,n+5,INF);
42         memset(cnt,0,sizeof cnt);
43         memset(fa,-1,sizeof fa);
44         int ans=0;
45
46         for(int i=1;i<=n;i++)
47         {
48             int low=lower_bound(d,d+i,a[i].y)-d-1;
49             cnt[i]=low+1;
50             ans=max(ans,cnt[i]);
51             d[low+1]=a[i].y;
52         }
53
54         printf("%d\n",ans);
55         int u;
56         for(int i=n;i>=1;i--)
57             if(cnt[i]==ans)
58             {
59                 u=i;
60                 break;
61             }
62
63         printf("%d",a[u].num);
64         int pre=u;
65         for(int i=u-1;i>=1;i--)
66         {
67             if(a[i].y<a[pre].y && cnt[i]==cnt[pre]-1)
68             {
69                 printf(" %d",a[i].num);
70                 pre=i;
71             }
72         }
73         printf("\n");
74     }
75     return 0;
76 }
时间: 2024-11-03 05:34:46

ZOJ3519-Beautiful People:最长上升子序列的变形的相关文章

hdu5282 最长公共子序列的变形

http://acm.hdu.edu.cn/showproblem.php?pid=5282 Problem Description Xuejiejie loves strings most. In order to win the favor of her, a young man has two strings X, Y to Xuejiejie. Xuejiejie has never seen such beautiful strings! These days, she is very

SGU 199 - Beautiful People 最长上升子序列LIS

要邀请n个人参加party,每个人有力量值strength Si和魅力值 beauty Bi,如果存在两人S i ≤ S j and B i ≥ B j 或者  S i ≥ S j and B i ≤ B j 他们两个会产生冲突,问在不产生冲突的条件下,最多能邀请到几个人? [LIS]一开始将所有人按照Si升序排序,Si相同的按照Bi值降序排列,在这个基础上答案就是Bi的最长上升子序列的长度. 为什么Si相同时按照Bi值降序排列? 由求出的子序列时严格递增序列,如果对于相同的Si,Bi是递增,那

导弹拦截(最长下降子序列)变形

题目描述 Description 某国为了防御敌国的导弹袭击,发展出一种导弹拦截系统.但是这种导弹拦截系统有一个缺陷:虽然它的第一发炮弹能够到达任意的高度,但是以后每一发炮弹都不能高于前一发的高度.某天,雷达捕捉到敌国的导弹来袭.由于该系统还在试用阶段,所以只有一套系统,因此有可能不能拦截所有的导弹. 输入描述 Input Description 输入导弹依次飞来的高度(雷达给出的高度数据是不大于30000的正整数) 输出描述 Output Description 输出这套系统最多能拦截多少导弹

vijos P1028 最长上升子序列变形题

#include<iostream> #include<cstdio> #include<cstring> #include<map> #include<string> #include<vector> #include<algorithm> using namespace std; bool judge(const string &aa,const string &bb) { for(int i=0;i&

java最长升序子序列

最长升序子序列是最长公共子序列的变形. 只要将字符串升序排序后与原字符串求最长公共子序列即可. 以下提供一个工具类可以传入任何形式的数组.(添加新类型的数组时构造方法要自己加). package com.leejuen.string; import java.lang.reflect.Array; import java.util.Arrays; public class LCS { private Integer len; private Object str1; private Object

SGU 199 Beautiful People 二维最长递增子序列

题目链接: http://acm.hust.edu.cn/vjudge/problem/viewProblem.action?id=20885 题意: 求二维最长严格递增子序列. 题解: O(n^2)的算法很好想,不过这里会t掉,只能O(nlogn) 于是用二分来维护: 先把所有的数按x递增排序,x相同的按y递减排序(这里之所以要按y递减排序是因为为了写代码方便,递减的话你后面基本就只要考虑y的大小,如果不递减,你还要考虑x的大小的,具体的可以自己思考一下) 排完序之后我们接下来就只考虑y的大小

hdu 4352 数位dp(最长上升子序列的长度为k的个数)

http://acm.hdu.edu.cn/showproblem.php?pid=4352 Problem Description #define xhxj (Xin Hang senior sister(学姐)) If you do not know xhxj, then carefully reading the entire description is very important. As the strongest fighting force in UESTC, xhxj grew

ASC(1)G(最长上升子序列)

G - Beautiful People Time Limit: 10000/5000MS (Java/Others) Memory Limit: 128000/64000KB (Java/Others)     Special Judge SubmitStatus Problem Description The most prestigious sports club in one city has exactly N members. Each of its members is stron

14-高效求最长公共子序列(二维数组存不下)

/*                                   See LCS again时间限制:1000 ms  |  内存限制:65535 KB难度:3 描述 There are A, B two sequences, the number of elements in the sequence is n.m; Each element in the sequence are different and less than 100000. Calculate the length