【问题标题】:Maximum Length of Pairs in increasing order [duplicate]对的最大长度按递增顺序[重复]
【发布时间】:2013-08-02 14:05:15
【问题描述】:

给定 n 对数字,第一个数字总是小于第二个数字。当且仅当 b

例如{ (1,2), (3,4), (5,7), (9,10), (7,9), (8,9), (0,6) }

所以输出应该是:{(1,2), (3,4), (5,7), (8,9), (9,10)}

我的算法如下:

 1. Sort the list according to the 2nd number of elements
i.e.`{ (1,2), (3,4), (0,6), (5,7), (7,9), (8,9), (9,10)  }`
 2. choose the first element from the list  i.e. `(1,2)`
 3. for each element e in the list left
      4. choose this element e if the first number of the element is greater than the 2nd number of the previous element. i.e. after `(1,2)` choose `(3,4)` because `3 > 2.`

经过上述算法,您将得到{(1,2), (3,4), (5,7), (8,9), (9,10)}的输出。

请让我知道算法的正确性。谢谢。

编辑:

更直观的正确性证明:

证明:在链中包含更多对的唯一方法是用 Y 值较小的一对替换一对,以允许下一个 对具有较小的 X 值,可能适合另一对 以前装不下。如果您将一对替换为具有相同 Y 的一对 价值,你一无所获。如果替换的 Y 值较大,则所有 你所做的可能会阻止一些以前适合的对。

因为这些对是按 Y 值排序的,所以您永远找不到 Y 值较小的替代品。在排序中“向前” 对,它们都将具有相同或更大的 Y 值。看着 “向后”,最初从链中消除的任何东西都是 因为X值不够高,还是会这样。

这取自here

【问题讨论】:

  • 你为什么把 (7,9) 排除在外?为什么它不在对 (5,7) 之后?
  • 给定您的示例的另一个有效链是 {(1,2), (3,4), (5,7), (7,9), (9,10)}。您是否希望找到两个/所有链,无论是链、最大长度链还是其他?
  • 我认为这行不通,因为它很贪心。排除包含的一个元素可能会产生更长的链条。我认为这需要作为一个动态程序来完成。
  • 这个问题要求进行代码审查,但没有提出问题。这个问题更适合 CodeReview。
  • 不管怎样,你的算法是正确的。稍后我可能会发布一个证明。

标签: java algorithm


【解决方案1】:

没错。这是一个证明:

s1, s2, ..., sl 是您的算法找到的对,i1, i2, ..., ik 是最优解。

我们有:

l == k => your algorithm is obviously correct, since it's clear that
          it doesn't produce invalid solutions;

l > k => this would contradict our hypothesis that i1, ..., ik is optimal,
         so it makes no sense to bother with this;

l < k => this would mean that your algorithm is wrong. 
         Let's assume this is the case.

假设i1 != s1。在这种情况下,我们可以在最优解中将i1 替换为s1,因为s1 是完成时间最短的对。所以s1, i2, ..., ik 仍然是最佳解决方案。

t &lt;= l 成为st != it 的第一个索引。因此,s1, s2, ..., s[t-1], it, ... 是一个最优解。我们可以将it 替换为st,因为:

  • st 不是最优解的第一个 t-1 元素的一部分;
  • st 不是 i[t+1], ..., ik 的一部分。如果是,那意味着stit 完成之后开始,这将与算法选择st 的方式相矛盾。

因此,以这种方式继续下去,我们的最佳解决方案是s1, s2, ..., sl, ..., ik。这意味着可以在sl之后添加更多对,但这与算法的工作方式相矛盾,所以我们有l = k,并且算法是正确的。

【讨论】:

    【解决方案2】:
    1. pair (c, d) 可以跟随一对 (a, b) iff b &lt;= c
    2. (c, d)有约束d &gt; c

    所以我们可以说

    b <= c
    

    变成

    b < d because d > c
    

    因此最长的序列将从最小的第二个元素开始。因此,您根据第二个元素对它们进行排序选择第一个元素并根据您的原始条件进行比较b &lt;= c

    算法是正确的。当您获得第一个元素(贪心)时,您将保持原始约束不变,即b &lt;= c

    注意: 您不能使用b &lt; d 条件来比较排序后的元素,因为您无法从b &lt; d 推断出b &lt;= c(原始条件),但可以采用其他方式。

    【讨论】:

    • 我喜欢这个证明。更直观。 +1
    【解决方案3】:

    这个问题可以解决的方法太多了 相同类型的问题已经存在检查它 给你 n 对数字。在每一对中,第一个数字总是小于第二个数字。如果 b

    你可以去这里,那里有很多有用的资源

    MaximumLengthChainoofPairs

    LongestIncreasingSequence

    【讨论】:

    • 这是评论,不是答案。
    • 这些不是一回事,因为它们涉及按元素出现的顺序选择元素。
    • @Joel (0,6) 怎么样?
    • @Shivaram Kalra为什么不考虑(0,6)..这是极端情况或最长的连续
    • @Envious 我的算法与您发布的算法不同。我知道这可以在 LIS 中解决,但这是 O(NLogN) 算法,我觉得更容易理解。我知道 LIS 可以在 O(NLogN) 中解决的另一件事,但这有点棘手。谢谢。
    猜你喜欢
    • 2014-08-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-01-31
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多