【问题标题】:Longest Subsequence with given conditions给定条件下的最长子序列
【发布时间】:2018-01-25 10:44:55
【问题描述】:

给定一个数组A,它有n个元素和整数k。我需要找到从数组的第一个元素开始的最长子序列,并且子序列的总权重≤k。
子序列的权重定义为所选子序列的连续元素的绝对差之和

约束 : -
1 ≤ n ≤10^5
0≤k≤50
0≤Ai≤50
示例:n= 4, k = 5, A = [1, 2, 50, 6]

答案:最长的有效子序列[1, 2, 6],长度为3。 子序列的权重是|1 - 2| + |2 - 6| = 1 + 4 = 5。 请注意,子序列从数组的第一个元素开始。

我认为这个问题可以使用动态规划来解决,但我无法提出递归关系。

【问题讨论】:

    标签: arrays algorithm data-structures dynamic-programming


    【解决方案1】:

    假设您正在处理数组 A,选择要包含在子序列中的值。在每个步骤中,您可以 (a) 包含当前值,或者 (b) 不包含它。如果你记住了这两个选项中更好的一个,那么应该可以让动态编程工作。

    在伪代码中,您的函数应该如下所示:

    int longest_subseq(ix, available_weight, last_val):
        # Parameters:
        # ix = an index into array A (assumed to have global scope)
        # available_weight = the remaining weight avaiable for the subsequence
        #                    starting at ix
        # last_val = the last value in the subsequence from A[0] through A[ix-1]
    
        # When first called, create a DP array of 10^5 × 51 × 51 elements
        # (This will use about 1GB of memory, which I assume is OK)
        if DP is undefined:
            DP = new array(100001, 51, 51)
            initialize every element of DP to -1
    
        # Return memoized value if available
        v = DP[ix, available_weight, last_val]
        if v >= 0:
            return v
    
        # Check for end conditions
        if ix == n or available_weight == 0:
            return 0
    
        # Otherwise you have two options; either include A[ix] in the
        # subsequence, or don't include it
        len0 = longest_subseq(ix+1, available_weight, last_val)
        if abs(A[ix] - last_val) > available_weight:
            DP[ix, available_weight, last_val] = len0
            return len0
        len1 = 1 + longest_subseq(ix+1, available_weight-abs(A[ix]-last_val), A[ix])
        if len0 > len(1):
            DP[ix, available_weight, last_val] = len0
            return len0
        else:
            DP[ix, available_weight, last_val] = len1
            return len1
    

    如果您随后调用longest_subseq(0, k, A[0]),该函数应在合理的时间内返回正确答案。

    【讨论】:

    • 我认为我们可以利用这样一个事实,即当你有 [a,b,c] 时,只有 a 和 c 很重要,因为 b 被取消了。
    • @squeamish-ossifrage,您的解决方案给出了错误答案:n = 5, k = 0, and A = [1, 1, 1, 1, 1] 答案应该是 5 = [1 , 1, 1, 1, 1],请你看一下。
    • 啊,好的。 if A[ix] > available_weight 向下约 2/3 应为 if abs(A[ix] - last_val) > available_weight。可能还有其他错误,但这只是伪代码。如果你能弄清楚它想要做什么,那么获得一个有效的实现应该不会太难。
    • @squeamishossifrage 我尝试使用 n = 9、k = 10 和 A = [5 2 4 9 1 3 2 4 5],但它再次给了我错误的答案......你能帮忙吗我出去......这是我的代码链接:ideone.com/6kI7iZ 正确答案应该是 7 [5 2 4 3 2 4 5] 但给出 5 作为答案。
    猜你喜欢
    • 2014-12-25
    • 1970-01-01
    • 2023-03-04
    • 2015-09-02
    • 2017-02-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多