题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1160
题意:给你若干个老鼠的体型(或者重量)和其对应的速度,让你输出由这些老鼠当中若干只老鼠组成的最长序列(体型严格递增,速度严格递减)长度,还有其对应的编号。
分析:dp操作和lis有点类似,只不过要先对数据进行一波预处理,写一发重载,以老鼠的速度从高到低进行排序(这样有利于后面进行的dp),每次dp+1就记录上一个的路径,然后输出。
下面是代码(蜜汁AC):
#include<cstdio>
#include<cstring>
#include<string>
#include<sstream>
#include<iostream>
#include<set>
#include<map>
#include<queue>
#include<vector>
#include<algorithm>
#include<cctype>
#include<math.h>
#include<stdlib.h>
#include<stack>
#include<ctime>
#define mst(a,b) memset(a,b,sizeof(a))
#define ALL(x) x.begin(),x.end()
#define INS(x) inserter(x,x.begin())
#define pii pair<int,int>
const int N = 1e9;
const int mod=(int)1e9+7;
const int INF=0x3f3f3f3f;
const long long LINF=(1LL<<62);
typedef long long LL;
//#define LOCAL
const double PI = acos(-1.0);
const int maxn=1e3+5;
using namespace std;
int dp[1005];
struct mouse
{
int siz, speed, num;
mouse *pre;
bool operator < (const mouse &t) const{
return speed>t.speed; //重载<,根据速度由高到低排序。
}
}a[1005];
int main()
{
#ifdef LOCAL
freopen("test.txt", "r", stdin);
#endif // LOCAL
//ios::sync_with_stdio(false);
int n, k, temp = 0, ans = -1, ansnum;
for(int i = 0; i < 1005; i++) dp[i] = 1;
while(~scanf("%d%d", &n, &k)) {a[temp].siz = n; a[temp].speed = k; a[temp].num = temp+1; temp++;}
sort(a,a+temp);
for(int i = 0 ; i < temp; i++){
for(int j = 0; j < i; j++){
if(a[i].siz>a[j].siz){
if(a[i].speed<a[j].speed){
if(dp[j]+1>dp[i]){
dp[i] = dp[j]+1;
a[i].pre = &a[j]; //记录路径
}
}
}
}
if(ans<dp[i]){
ans = dp[i];
ansnum = i;
}
}
stack<int> st; //利用stack的特性FILO
mouse kk = a[ansnum];
while(kk.pre){
st.push(kk.num);
kk = *kk.pre;
}
st.push(kk.num);
printf("%d\n", ans);
while(!st.empty()){
int dd = st.top();st.pop();
printf("%d\n", dd);
}
return 0;
}
第一条靠自己想写出的kuangbin基础dp专题题目QAQ。