题意:
给你n个二元组(u,v),要你求最长的u是递增,v是递减的子序列。
思路:
这个题乍一看不就是个最长上升子序列吗?然后满足一个约束v是递减的求不就行了?
思路确实是这样,不过需要预处一下按u递增v递减排序(因为满足约束并且可以往回找),这样可以把所有的子序列全部找出来,如果不预处理是找不出来的,因为可能要往回找,不太好处理,所以预处理了,前提是子序列不连续的,并且是可以往回找的(只要满足条件,最长上升子序列是不可以往回找了,注意区别)连续就不行。然后就是最长子序列问题了,需要处理一下路径(没有处理好细节,浪费了很多时间)。
代码:

#include<bits/stdc++.h>
using namespace std;

const int maxn = 1e3 + 10;
const int inf = 0x3f3f3f3f;
struct node{
    int x,y,id;
    node(){}
    node(int a,int b):x(a),y(b){}
    node(int a,int b,int c):x(a),y(b),id(c){}
};
struct node a[maxn];
int dp[maxn],path[maxn];
void dfs(int n){
    if(n == 1)return;
    else {
        dfs(path[n]);
        cout<<n<<endl;
    }
}
bool cmp(node a,node b){
    if(a.x == b.x)
    return a.y > b.y;
    return a.x < b.x;
}
int main(){
    int cnt = 1;
    while(scanf("%d%d",&a[cnt].x,&a[cnt].y)!=EOF){
        a[cnt].id = cnt;
        cnt ++;
    }
    cnt --;
    dp[1] = 1;
    sort(a+1,a+1+cnt,cmp);
    for(int i = 1; i <= cnt; i++)path[i] = 1;
    for(int i = 1; i <= cnt ; i++){
        int M = 0 ;
        for(int j = 1; j < i ; j++){
            if(a[j].x < a[i].x && a[j].y > a[i].y)
            if(dp[j] > M){M = dp[j];path[a[i].id] = a[j].id;} 
        }
        dp[i] = M + 1;
    }
    int ans = 0;int sb = 0;
    for(int i = 1; i <= cnt; i++){
        if(dp[i] > ans){
            ans = dp[i];sb = i;
        }
    }
    //for(int i = 1; i <= cnt ; i++)cout<<path[i]<<' ';
    cout<<ans<<endl;
    dfs(a[sb].id);
}

所有解:

#include<bits/stdc++.h>
using namespace std;

const int maxn = 1e3 + 10;
const int inf = 0x3f3f3f3f;
struct node{
    int x,y,id;
    node(){}
    node(int a,int b):x(a),y(b){}
    node(int a,int b,int c):x(a),y(b),id(c){}
}a[maxn];
int dp[maxn],path[maxn],ans;
void dfs(int n,int dep){
    if(n == 1)return;
    else {
        dfs(path[n],dep + 1);
		cout<<n;
        if(dep != 1) 
		cout<<" - > ";
    }
}
bool cmp(node a,node b){
    if(a.x == b.x)
    return a.y > b.y;
    return a.x < b.x;
}
int main(){
    int cnt = 1;
    while(scanf("%d%d",&a[cnt].x,&a[cnt].y)!=EOF){
        a[cnt].id = cnt;
        cnt ++;
    }
    cnt --;
    dp[1] = 1;
    sort(a+1,a+1+cnt,cmp);
    for(int i = 1; i <= cnt; i++){
    	cout<<a[i].id<<" "<<a[i].x <<" "<<a[i].y<<endl;
	}
    for(int i = 1; i <= cnt; i++)path[i] = 1;
    for(int i = 1; i <= cnt ; i++){
        int M = 0 ;
        for(int j = 1; j < i ; j++){
            if(a[j].x < a[i].x && a[j].y > a[i].y)
            if(dp[j] > M){M = dp[j];path[a[i].id] = a[j].id;} 
        }
        dp[i] = M + 1;
    }
    int sb = 0;
    vector<int>ve;
    for(int i = 1; i <= cnt; i++){
        if(dp[i] > ans){
            ans = dp[i];sb = i;
        }
    }
    ve.push_back(sb);
    for(int i = 1; i <= cnt; i++){
    	if(ans == dp[i] && i != sb){
    		ve.push_back(i);
		}
	}
    //for(int i = 1; i <= cnt ; i++)cout<<path[i]<<' ';
    cout<<"lenth :"<<ans<<endl;
    for(int i = 0; i < ve.size(); i++)
    dfs(a[ve[i]].id,1),cout<<endl;
}