HDU 1160 FatMouse‘s Speed
Posted jpphy0
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了HDU 1160 FatMouse‘s Speed相关的知识,希望对你有一定的参考价值。
链接
FatMouse’s Speed - http://acm.hdu.edu.cn/showproblem.php?pid=1160
分析
- LIS
- 动态规划
- 寻找“越胖越慢”证据,即寻找最长链
- 速度降序,体重升序的最长链;
- 每个长度的链保存一条,当链的最后一个重量变化时,复制前一个长度的链
- 另一种思路:按序列的下标分类,即每个元素一类【注意:与每个元素的值分一类的区别】
代码
等长— 值优先 【二维路径数组】
/* hdu 1160 FatMouse's Speed */
#include <bits/stdc++.h>
using namespace std;
#define MXN 1010
int dp[MXN], t[MXN][MXN];
struct FM{
int m, s, id;
}fm[MXN];
int main(){
int cnt = 0, len, pm;
while(scanf("%d %d", &fm[cnt+1].m, &fm[cnt+1].s) == 2){
cnt++;
fm[cnt].id = cnt;
}
sort(fm+1, fm+cnt+1, [](FM x, FM y){ return x.s > y.s;});
memset(dp, 0, sizeof dp);
memset(t, 0, sizeof t);
len = 1, dp[1] = 1, t[1][1] = 1;
for(int i = 2; i <= cnt; ++i) {
pm = lower_bound(dp+1, dp+len+1, i, [](int x, int y){
return fm[x].m < fm[y].m;
}) - dp;
if(pm == len+1) len++;
dp[pm] = i;
// 复制前一个链
for(int j = 1; j < pm; ++j) t[pm][j] = t[pm-1][j];
// 修改链的最后一个元素
t[pm][pm] = i;
}
printf("%d\\n", len);
for(int i = 1; i <= len; ++i) printf("%d\\n", fm[t[len][i]].id);
return 0;
}
等长— 值优先 【一维前驱路径数组】
// hdu 1160 FatMouse's Speed
#include <bits/stdc++.h>
using namespace std;
#define MXN 1010
int n = 0, len, dp[MXN], pre[MXN];
struct FM{
int w = 0, s = 0, id = 0;
bool operator<(FM x){ return s > x.s;}
}fm[MXN];
// ostream & operator<<(ostream & os, const FM x){
// os << "w = "<< x.w << " s = " << x.s << " id = " << x.id;
// return os;
// }
void print(int x){
if(x == 0) return;
print(pre[x]);
cout << fm[x].id << endl;
}
int main() {
int pos;
while(scanf("%d%d", &fm[n+1].w, &fm[n+1].s) == 2)
n++, fm[n].id = n;
sort(fm+1, fm+n+1);
memset(pre, 0, sizeof pre);
memset(dp, 0, sizeof dp);
len = 1, dp[1] = 1;
for(int i = 2; i <= n; ++i){
if(fm[i].w > fm[dp[len]].w){
pre[i] = dp[len];
dp[++len] = i;
}
else{
pos = lower_bound(dp+1, dp+len+1, i, [](int mid, int val){
return fm[mid].w < fm[val].w;
}) - dp;
pre[i] = dp[pos - 1];
dp[pos] = i;
}
}
printf("%d\\n", len);
print(dp[len]);
return 0;
}
按下标 — 长度优先【一维前驱路径数组】
/* hdu 1160 FatMouse's Speed */
#include <bits/stdc++.h>
using namespace std;
#define MXN 1010
int dp[MXN], pre[MXN];
struct FM{
int m, s, id;
}fm[MXN];
int main(){
int cnt = 0, len = 0, p;
while(scanf("%d %d", &fm[cnt+1].m, &fm[cnt+1].s) == 2){
cnt++;
fm[cnt].id = cnt;
}
sort(fm+1, fm+cnt+1, [](FM x, FM y){ return x.s > y.s;});
memset(dp, 0, sizeof dp);
memset(pre, 0, sizeof pre);
for(int i = 1; i <= cnt; ++i) {
for(int j = 0; j < i; ++j){
if(fm[i].m > fm[j].m && dp[i] < dp[j]+1){
pre[i] = j;
dp[i] = dp[j]+1;
}
}
}
for(int i= 1; i <= cnt; ++i) if(len < dp[i]) len = dp[i], p = i;
printf("%d\\n", len);
cnt = len;
while(p != 0){
dp[cnt--] = fm[p].id;
p = pre[p];
}
for(int i = 1; i <= len; ++i) printf("%d\\n", dp[i]);
return 0;
}
以上是关于HDU 1160 FatMouse‘s Speed的主要内容,如果未能解决你的问题,请参考以下文章
HDU 1160 FatMouse's Speed (动态规划最长下降子序列)
HDU - 1160 FatMouse's Speed(dp+路径记录)