最长(不)上升子序列(LIS与LDS问题)

对于LIS,如果下一个数大于目前最长序列数的最后一位,则将最长序列数+1,反之则直接用lower_bound()进行二分查找,找到第一个大于等于这个数的序列数,将它替换,此替换过程不影响最长序列的个数。

同理,对于LDS,如果下一个数小于等于目前最长序列数的最后一位,则最长序列数+1,反之利用upper_bound()进行二分查找,找到第一个大于这个数的序列数将之替换。

代码如下:

b[0] = a[0];
//最长不上升子序列
for (int i = 1; i < cnt; i++) {
    if (b[cnt1] >= a[i])
        b[++cnt1] = a[i];//序列向后移
    else {
        int x = upper_bound(b, b + cnt1, a[i], greater<int>()) - b;//降序查找
        b[x] = a[i];//找到第一个小于a[i],将它替换
    }
}
memset(b, 0, sizeof(b));
b[0] = a[0];
//最长上升子序列
for (int i = 1; i < cnt; i++) {
    if (a[i] > b[cnt2])
        b[++cnt2] = a[i];//序列向后移
    else {
        int x = lower_bound(b, b + cnt2, a[i]) - b;//升序查找
        b[x] = a[i];//找到第一个大于等于a[i],替换
    }
}

 

posted @ 2023-07-30 16:52  DLSQS  阅读(110)  评论(0)    收藏  举报