How to Get Minimum Moves to Equal Array Elements?


Given an array (non empty) of integers, find the number of minimum moves to make all elements equal. A move is to increment (n – 1) elements by one. For example, [1, 3] needs two moves to make all elements equal: [1, 3] – [2, 3] and [3, 3].

How to Move? Greedy Solution

The strategy of moves is to NOT pick the maximum value (Greedy Algorithm). Incrementing the maximum element is like going to the opposite direction e.g. [1, 4] needs 3 more moves to complete instead of [2, 3] which just needs 1 more move. It is also equivalent to decrementing the maximum element at each move. Therefore, we just need to count the number of moves for each element towards a global minimal.

1
2
3
4
5
6
7
8
9
10
11
12
class Solution {
public:
    int minMoves(vector<int>& nums) {
        int sum = 0;
        int v = INT_MAX;
        for (auto i: nums) {
            sum += i;
            v = min(i, v);
        }
        return sum - v * nums.size();
    }
};
class Solution {
public:
    int minMoves(vector<int>& nums) {
        int sum = 0;
        int v = INT_MAX;
        for (auto i: nums) {
            sum += i;
            v = min(i, v);
        }
        return sum - v * nums.size();
    }
};

C++ Syntax Sugar – Sum and Min

The above O(n) implementation is straightforward but you can also make it better by using the syntax sugar (or library to be more precise).

std::min_element

std::min_element returns the iterator of the minimal element. Get the value by dereferencing it.

1
2
3
4
5
6
7
8
9
10
11
class Solution {
public:
    int minMoves(vector<int>& nums) {
        int min = *std::min_element(nums.begin(), nums.end());
        int s = 0;
        for (auto i: nums) {
            s += i - min;
        }
        return s;
    }
};
class Solution {
public:
    int minMoves(vector<int>& nums) {
        int min = *std::min_element(nums.begin(), nums.end());
        int s = 0;
        for (auto i: nums) {
            s += i - min;
        }
        return s;
    }
};

Using a standard numeric algorithm library

The numeric allows you to sum the elements in a vector.

1
2
3
4
5
6
7
8
9
10
#include <numeric>
 
class Solution {
public:
    int minMoves(vector<int>& nums) {
        int min = *std::min_element(nums.begin(), nums.end());
        int sum = std::accumulate(nums.begin(), nums.end(), 0);
        return sum - min * nums.size();
    }
};
#include <numeric>

class Solution {
public:
    int minMoves(vector<int>& nums) {
        int min = *std::min_element(nums.begin(), nums.end());
        int sum = std::accumulate(nums.begin(), nums.end(), 0);
        return sum - min * nums.size();
    }
};

In fact, there are quite a few ways to sum the elements in a C++ vector. Pick your favorite!

1
2
3
4
5
6
7
8
// Classic for loop:
for (auto it = nums.begin(); it != nums.end(); ++it)
    sum += *it;
 
// C++11 and higher
std::for_each(nums.begin(), nums.end(), [&] (int n) {
    sum += n;
});
// Classic for loop:
for (auto it = nums.begin(); it != nums.end(); ++it)
    sum += *it;

// C++11 and higher
std::for_each(nums.begin(), nums.end(), [&] (int n) {
    sum += n;
});

–EOF (The Ultimate Computing & Technology Blog) —

GD Star Rating
loading...
413 words
Last Post: The C++ Static Code Analyser by Visual Studio
Next Post: How to Link Static Library in C/C++ using GCC compiler?

The Permanent URL is: How to Get Minimum Moves to Equal Array Elements?

Leave a Reply