📌  相关文章
📜  使数组不增加的最小增量/减量

📅  最后修改于: 2021-10-26 06:32:09             🧑  作者: Mango

给定一个数组 a,您的任务是将其转换为非递增形式,以便我们可以在可能的最小变化中将数组值递增或递减 1。

例子 :

Input : a[] = {3, 1, 2, 1}
Output : 1
Explanation :
We can convert the array into 3 1 1 1 by
changing 3rd element of array i.e. 2 
into its previous integer 1 in one step
hence only one step is required.

Input : a[] = {3, 1, 5, 1}
Output : 4
We need to decrease 5 to 1 to make array sorted
in non-increasing order.

Input : a[] = {1, 5, 5, 5}
Output : 4
We need to increase 1 to 5.

蛮力方法:我们考虑每个元素的两种可能性,并找到至少两种可能性。

有效方法:计算最终数组元素与当前数组元素之间的绝对差之和。因此,答案将是第 i 个元素与直到那时发生的最小元素之间的差值之和。为此,我们可以维护一个最小堆来查找到那时遇到的最小元素。在最小优先级队列中,我们将把元素和新元素与之前的最小值进行比较。如果找到新的最小值,我们将更新它,这是因为每个即将到来的下一个元素都应该小于目前找到的当前最小元素。在这里,我们计算差异,以便我们可以得到我们必须改变当前数字的程度,以便它等于或小于之前遇到的数字。最后,所有这些差异的总和将是我们的答案,因为这将给出我们必须更改元素的最终值。

下面是上述方法的实现:

C++
// CPP code to count the change required to
// convert the array into non-increasing array
#include 
using namespace std;
 
int DecreasingArray(int a[], int n)
{
    int sum = 0, dif = 0;
 
    // min heap
    priority_queue, greater > pq;
 
    // Here in the loop we will
    // check that whether the upcoming
    // element of array is less than top
    // of priority queue. If yes then we
    // calculate the difference. After
    // that we will remove that element
    // and push the current element in
    // queue. And the sum is incremented
    // by the value of difference
    for (int i = 0; i < n; i++) {
        if (!pq.empty() && pq.top() < a[i]) {
            dif = a[i] - pq.top();
            sum += dif;
            pq.pop();
        }
        pq.push(a[i]);
    }
 
    return sum;
}
 
// Driver Code
int main()
{
    int a[] = { 3, 1, 2, 1 };
    int n = sizeof(a) / sizeof(a[0]);
 
    cout << DecreasingArray(a, n);
 
    return 0;
}


Java
// Java code to count the change required to
// convert the array into non-increasing array
import java.util.PriorityQueue;
 
class GFG
{
    public static int DecreasingArray(int a[], int n)
    {
        int sum = 0, dif = 0;
 
        PriorityQueue pq = new PriorityQueue<>();
 
        // Here in the loop we will
        // check that whether the upcoming
        // element of array is less than top
        // of priority queue. If yes then we
        // calculate the difference. After
        // that we will remove that element
        // and push the current element in
        // queue. And the sum is incremented
        // by the value of difference
        for (int i = 0; i < n; i++)
        {
            if (!pq.isEmpty() && pq.element() < a[i])
            {
                dif = a[i] - pq.element();
                sum += dif;
                pq.remove();
            }
            pq.add(a[i]);
        }
     
    return sum;
    }
 
    // Driver Code
    public static void main(String[] args)
    {
         
        int[] a = {3, 1, 2, 1};
         
        int n = a.length;
 
        System.out.println(DecreasingArray(a, n));
    }
}
 
// This Code is contributed by sanjeev2552


Python3
# Python3 code to count the change required to
# convert the array into non-increasing array
from queue import PriorityQueue
 
def DecreasingArray(a, n):
     
    ss, dif = (0,0)
     
    # min heap
    pq = PriorityQueue()
 
    # Here in the loop we will
    # check that whether the upcoming
    # element of array is less than top
    # of priority queue. If yes then we
    # calculate the difference. After
    # that we will remove that element
    # and push the current element in
    # queue. And the sum is incremented
    # by the value of difference
    for i in range(n):
        tmp = 0
         
        if not pq.empty():
            tmp = pq.get()
            pq.put(tmp)
         
        if not pq.empty() and tmp < a[i]:
            dif = a[i] - tmp
            ss += dif
            pq.get()
         
        pq.put(a[i])
       
    return ss
     
# Driver code   
if __name__=="__main__":
     
    a = [ 3, 1, 2, 1 ]
    n = len(a)
  
    print(DecreasingArray(a, n))
     
# This code is contributed by rutvik_56


C#
// C# code to count the change required to
// convert the array into non-increasing array
using System;
using System.Collections.Generic;
class GFG
{
    static int DecreasingArray(int[] a, int n)
    {
        int sum = 0, dif = 0;
      
        // min heap
        List pq = new List();
      
        // Here in the loop we will
        // check that whether the upcoming
        // element of array is less than top
        // of priority queue. If yes then we
        // calculate the difference. After
        // that we will remove that element
        // and push the current element in
        // queue. And the sum is incremented
        // by the value of difference
        for (int i = 0; i < n; i++)
        {
            if (pq.Count > 0 && pq[0] < a[i])
            {
                dif = a[i] - pq[0];
                sum += dif;
                pq.RemoveAt(0);
            }
            pq.Add(a[i]);
            pq.Sort();
        }
      
        return sum;
    }  
 
  // Driver code
  static void Main()
  {
    int[] a = { 3, 1, 2, 1 };
    int n = a.Length;
  
    Console.Write(DecreasingArray(a, n));
  }
}
 
// This code is contributed by divyeshrabadiya07.


输出:
1

时间复杂度:O(n log(n))
空间复杂度: O(n)
另请参阅:以最少的更改转换为严格递增的数组。

如果您希望与专家一起参加现场课程,请参阅DSA 现场工作专业课程学生竞争性编程现场课程