📜  构成排序序列的最小删除数

📅  最后修改于: 2021-04-24 04:53:55             🧑  作者: Mango

给定一个由n个整数组成的数组。任务是从数组中删除或删除最小数量的元素,以便当其余元素以相同的顺序放置时,形成递增的排序序列

例子 :

Input : {5, 6, 1, 7, 4}
Output : 2
Removing 1 and 4
leaves the remaining sequence order as
5 6 7 which is a sorted sequence.

Input : {30, 40, 2, 5, 1, 7, 45, 50, 8}
Output : 4

一个简单的解决方案是一个接一个地删除所有子序列,并检查其余元素集是否按排序顺序排列。该解决方案的时间复杂度是指数级的。

一种有效的方法使用找到给定序列的最长递增子序列的长度的概念。

算法:

-->arr be the given array.
-->n number of elements in arr.
-->len be the length of longest
   increasing subsequence in arr.
-->// minimum number of deletions
   min = n - len
C++
// C++ implementation to find 
// minimum number of deletions 
// to make a sorted sequence
#include 
using namespace std;
  
/* lis() returns the length
   of the longest increasing 
   subsequence in arr[] of size n */
int lis( int arr[], int n )
{
    int result = 0;
    int lis[n];
  
    /* Initialize LIS values
    for all indexes */
    for (int i = 0; i < n; i++ )
        lis[i] = 1;
  
    /* Compute optimized LIS 
       values in bottom up manner */
    for (int i = 1; i < n; i++ )
        for (int j = 0; j < i; j++ )
            if ( arr[i] > arr[j] &&
                 lis[i] < lis[j] + 1)
            lis[i] = lis[j] + 1;
  
    /* Pick resultimum 
    of all LIS values */
    for (int i = 0; i < n; i++ )
        if (result < lis[i])
            result = lis[i];
  
    return result;
}
  
// function to calculate minimum
// number of deletions
int minimumNumberOfDeletions(int arr[], 
                             int n)
{
    // Find longest increasing 
    // subsequence
    int len = lis(arr, n);
  
    // After removing elements 
    // other than the lis, we 
    // get sorted sequence.
    return (n - len);
}
  
// Driver Code
int main()
{
    int arr[] = {30, 40, 2, 5, 1,
                   7, 45, 50, 8};
    int n = sizeof(arr) / sizeof(arr[0]);
    cout << "Minimum number of deletions = "
         << minimumNumberOfDeletions(arr, n);
    return 0;
}


Java
// Java implementation to find
// minimum number of deletions 
// to make a sorted sequence
  
class GFG
{
    /* lis() returns the length 
    of the longest increasing 
    subsequence in arr[] of size n */
    static int lis( int arr[], int n )
    {
        int result = 0;
        int[] lis = new int[n];
      
        /* Initialize LIS values 
        for all indexes */
        for (int i = 0; i < n; i++ )
            lis[i] = 1;
      
        /* Compute optimized LIS 
           values in bottom up manner */
        for (int i = 1; i < n; i++ )
            for (int j = 0; j < i; j++ )
                if ( arr[i] > arr[j] &&
                    lis[i] < lis[j] + 1)
                    lis[i] = lis[j] + 1;
      
        /* Pick resultimum of
        all LIS values */
        for (int i = 0; i < n; i++ )
            if (result < lis[i])
                result = lis[i];
      
        return result;
    }
      
    // function to calculate minimum
    // number of deletions
    static int minimumNumberOfDeletions(int arr[], 
                                        int n)
    {
        // Find longest 
        // increasing subsequence
        int len = lis(arr, n);
      
        // After removing elements 
        // other than the lis, we get
        // sorted sequence.
        return (n - len);
    }
  
    // Driver Code
    public static void main (String[] args) 
    {
        int arr[] = {30, 40, 2, 5, 1,
                       7, 45, 50, 8};
        int n = arr.length;
        System.out.println("Minimum number of" +
                               " deletions = " +
              minimumNumberOfDeletions(arr, n));
    }
}
  
/* This code is contributed by Harsh Agarwal */


Python3
# Python3 implementation to find 
# minimum number of deletions to
# make a sorted sequence
  
# lis() returns the length 
# of the longest increasing
# subsequence in arr[] of size n
def lis(arr, n):
  
    result = 0
    lis = [0 for i in range(n)]
  
    # Initialize LIS values
    # for all indexes 
    for i in range(n):
        lis[i] = 1
  
    # Compute optimized LIS values 
    # in bottom up manner 
    for i in range(1, n):
        for j in range(i):
            if ( arr[i] > arr[j] and
                lis[i] < lis[j] + 1):
                lis[i] = lis[j] + 1
  
    # Pick resultimum 
    # of all LIS values 
    for i in range(n):
        if (result < lis[i]):
            result = lis[i]
  
    return result
  
# Function to calculate minimum
# number of deletions
def minimumNumberOfDeletions(arr, n):
  
    # Find longest increasing 
    # subsequence
    len = lis(arr, n)
  
    # After removing elements 
    # other than the lis, we 
    # get sorted sequence.
    return (n - len)
  
  
# Driver Code
arr = [30, 40, 2, 5, 1, 
          7, 45, 50, 8]
n = len(arr)
print("Minimum number of deletions = ",
      minimumNumberOfDeletions(arr, n))
          
# This code is contributed by Anant Agarwal.


C#
// C# implementation to find
// minimum number of deletions 
// to make a sorted sequence
using System;
  
class GfG 
{
      
    /* lis() returns the length of
    the longest increasing subsequence
    in arr[] of size n */
    static int lis( int []arr, int n )
    {
        int result = 0;
        int[] lis = new int[n];
      
        /* Initialize LIS values for
        all indexes */
        for (int i = 0; i < n; i++ )
            lis[i] = 1;
      
        /* Compute optimized LIS values
        in bottom up manner */
        for (int i = 1; i < n; i++ )
            for (int j = 0; j < i; j++ )
                if ( arr[i] > arr[j] &&
                     lis[i] < lis[j] + 1)
                  lis[i] = lis[j] + 1;
      
        /* Pick resultimum of all LIS
        values */
        for (int i = 0; i < n; i++ )
            if (result < lis[i])
                result = lis[i];
      
        return result;
    }
      
    // function to calculate minimum
    // number of deletions
    static int minimumNumberOfDeletions(
                        int []arr, int n)
    {
          
        // Find longest increasing
        // subsequence
        int len = lis(arr, n);
      
        // After removing elements other
        // than the lis, we get sorted
        // sequence.
        return (n - len);
    }
  
    // Driver Code
    public static void Main (String[] args) 
    {
        int []arr = {30, 40, 2, 5, 1, 
                       7, 45, 50, 8};
        int n = arr.Length;
        Console.Write("Minimum number of" + 
                          " deletions = " + 
         minimumNumberOfDeletions(arr, n));
    }
}
  
// This code is contributed by parashar.


PHP
 $arr[$j] &&
                $lis[$i] < $lis[$j] + 1)
                $lis[$i] = $lis[$j] + 1;
  
    /* Pick resultimum of 
    all LIS values */
    for ($i = 0; $i < $n; $i++ )
        if ($result < $lis[$i])
            $result = $lis[$i];
  
    return $result;
}
  
// function to calculate minimum
// number of deletions
function minimumNumberOfDeletions($arr, $n)
{
    // Find longest increasing
    // subsequence
    $len = lis($arr, $n);
  
    // After removing elements 
    // other than the lis, we
    // get sorted sequence.
    return ($n - $len);
}
  
// Driver Code
$arr = array(30, 40, 2, 5, 1, 
               7, 45, 50, 8);
$n = sizeof($arr) / sizeof($arr[0]);
echo "Minimum number of deletions = " , 
    minimumNumberOfDeletions($arr, $n);
  
// This code is contributed by nitin mittal.
?>


输出 :

Minimum number of deletions = 4 

时间复杂度: O(n 2 )

通过找到最长增加的子序列大小(N Log N),可以将时间复杂度降低到O(nlogn)