Open In App

Convert Array such that no two even or odd numbers are adjacent

Given an array arr[], the task is to print the minimum number of operations required to convert the array such that neither two even elements are adjacent nor two odd numbers are adjacent. In other words arr[i]%2 != arr[i+1]%2. For that, you can perform certain operations. (consider 0-based indexing)

Examples:



Input: arr[] = [4, 10, 10, 6, 2]
Output: 2
Explanation: Choose index 1 and divide  it by 2: the new array is [4, 5, 10, 6, 2].
Choose index 3 and divide it by 2: the new array is [4, 5, 10, 3, 2].

Input: arr[] = [4, 20, 10, 6, 2]
Output: 3
Explanation: Choose index 1 and divide it by 2 two times: the new array is [4, 5, 10, 6, 2].
Choose index 3 and divide it by 2: the new array is [4, 5, 10, 3, 2].



Approach: To solve the problem follow the below idea:

The only two possible orders are:

  • odd, even, odd, even, odd, even, ……..
  • even, odd, even, odd, even, odd, ……..

Precompute and store the number of operations needed by each element of the array to convert it to even and odd forms and then try two permutations. In each permutation, the total number of operations is calculated by adding the minimum number of operations required to convert each element in the permutation and print the minimum of the two permutations.

Follow the steps to solve the problem:

Below is the implementation for the above approach:




// C++ code for the above approach:
#include <bits/stdc++.h>
using namespace std;
 
int convertArray(vector<int> arr)
{
 
    // Size of the vector
    int n = arr.size();
 
    // Initializing the vector dp to store
    // count of operations
    vector<pair<int, int> > dp(n);
 
    // Precomputing of values how many
    // steps required to convert the
    // current element to odd and even
    for (int i = 0; i < n; i++) {
 
        if (arr[i] % 2 == 0) {
            dp[i].second = 0;
 
            int cnt = 0;
            int x = arr[i];
 
            while (x % 2 == 0) {
                x = x / 2;
                cnt++;
            }
 
            dp[i].first = cnt;
        }
 
        else {
            dp[i].first = 0;
 
            int cnt = 0;
            int x = arr[i];
 
            while (x % 2 != 0) {
                x = x / 2;
                cnt++;
            }
 
            dp[i].second = cnt;
        }
    }
 
    // Trying (odd even odd even...)
    // permutaion
    int ans1 = 0;
 
    for (int i = 0; i < n; i++) {
        if (i % 2 == 0) {
            ans1 += dp[i].first;
        }
        else
            ans1 += dp[i].second;
    }
 
    // Trying (even odd even odd ...)
    // permutaion
    int ans2 = 0;
 
    for (int i = 0; i < n; i++) {
        if (i % 2 == 0) {
            ans2 += dp[i].second;
        }
        else
            ans2 += dp[i].first;
    }
 
    return min(ans1, ans2);
}
 
// Driver funtion
int main()
{
 
    vector<int> arr = { 4, 20, 10, 6, 2 };
    int steps = convertArray(arr);
 
    // Function Call
    cout << steps << endl;
    return 0;
}




/*package whatever // do not write package name here */
 
import java.io.*;
import java.lang.*;
 
class GFG {
 
    static int convertArray(int arr[], int n)
    {
 
        // initializing the vector dp to store count of
        // operations
 
        int[][] dp = new int[n][2];
 
        // precomputing of values how many steps required to
        // convert the current element to odd and even
        for (int i = 0; i < n; i++) {
 
            if (arr[i] % 2 == 0) {
                dp[i][1] = 0;
 
                int cnt = 0;
                int x = arr[i];
 
                while (x % 2 == 0) {
                    x = x / 2;
                    cnt++;
                }
 
                dp[i][0] = cnt;
            }
 
            else {
                dp[i][0] = 0;
 
                int cnt = 0;
                int x = arr[i];
 
                while (x % 2 != 0) {
                    x = x / 2;
                    cnt++;
                }
 
                dp[i][1] = cnt;
            }
        }
 
        // trying (odd even odd even...) permutaion
        int ans1 = 0;
 
        for (int i = 0; i < n; i++) {
            if (i % 2 == 0) {
                ans1 += dp[i][0];
            }
            else
                ans1 += dp[i][1];
        }
 
        // trying (even odd even odd ...) permutaion
        int ans2 = 0;
 
        for (int i = 0; i < n; i++) {
            if (i % 2 == 0) {
                ans2 += dp[i][1];
            }
            else
                ans2 += dp[i][0];
        }
 
        // returning the minimum of the 2 values
        return Math.min(ans1, ans2);
    }
 
    public static void main(String[] args)
    {
        int[] arr = { 4, 20, 10, 6, 2 };
        int n = arr.length;
 
        int steps = convertArray(arr, n);
        System.out.println(steps);
    }
}




def convertArray(arr):
 
    # Size of the list
    n = len(arr)
 
    # Initializing the list dp to store
    # count of operations
    dp = [(0, 0)] * n
 
    # Precomputing of values how many
    # steps required to convert the
    # current element to odd and even
    for i in range(n):
 
        if arr[i] % 2 == 0:
            dp[i] = (0, 0)
 
            cnt = 0
            x = arr[i]
 
            while x % 2 == 0:
                x //= 2
                cnt += 1
 
            dp[i] = (cnt, 0)
 
        else:
            dp[i] = (0, 0)
 
            cnt = 0
            x = arr[i]
 
            while x % 2 != 0:
                x //= 2
                cnt += 1
 
            dp[i] = (0, cnt)
 
    # Trying (odd even odd even...)
    # permutation
    ans1 = 0
 
    for i in range(n):
        if i % 2 == 0:
            ans1 += dp[i][0]
        else:
            ans1 += dp[i][1]
 
    # Trying (even odd even odd ...)
    # permutation
    ans2 = 0
 
    for i in range(n):
        if i % 2 == 0:
            ans2 += dp[i][1]
        else:
            ans2 += dp[i][0]
 
    return min(ans1, ans2)
 
# Driver function
if __name__ == '__main__':
    arr = [4, 20, 10, 6, 2]
    steps = convertArray(arr)
 
    # Function Call
    print(steps)




// C# code to implement the approach
using System;
 
class GFG {
 
    static int convertArray(int[] arr, int n)
    {
 
        // initializing the vector dp to store count of
        // operations
 
        int[][] dp = new int[n][];
        for (int i = 0; i < n; i++)
        {
            dp[i] = new int[2];
        }
 
        // precomputing of values how many steps required to
        // convert the current element to odd and even
        for (int i = 0; i < n; i++) {
 
            if (arr[i] % 2 == 0) {
                dp[i][1] = 0;
 
                int cnt = 0;
                int x = arr[i];
 
                while (x % 2 == 0) {
                    x = x / 2;
                    cnt++;
                }
 
                dp[i][0] = cnt;
            }
 
            else {
                dp[i][0] = 0;
 
                int cnt = 0;
                int x = arr[i];
 
                while (x % 2 != 0) {
                    x = x / 2;
                    cnt++;
                }
 
                dp[i][1] = cnt;
            }
        }
 
        // trying (odd even odd even...) permutaion
        int ans1 = 0;
 
        for (int i = 0; i < n; i++) {
            if (i % 2 == 0) {
                ans1 += dp[i][0];
            }
            else
                ans1 += dp[i][1];
        }
 
        // trying (even odd even odd ...) permutaion
        int ans2 = 0;
 
        for (int i = 0; i < n; i++) {
            if (i % 2 == 0) {
                ans2 += dp[i][1];
            }
            else
                ans2 += dp[i][0];
        }
 
        // returning the minimum of the 2 values
        return Math.Min(ans1, ans2);
    }
 
    public static void Main()
    {
        int[] arr = { 4, 20, 10, 6, 2 };
        int n = arr.Length;
 
        int steps = convertArray(arr, n);
        Console.WriteLine(steps);
    }
}
 
// This code is contributed by Pushpesh Raj




function convertArray(arr, n) {
  let dp = new Array(n).fill().map(() => new Array(2).fill(0));
 
  for (let i = 0; i < n; i++) {
    if (arr[i] % 2 === 0) {
      dp[i][1] = 0;
 
      let cnt = 0;
      let x = arr[i];
 
      while (x % 2 === 0) {
        x = x / 2;
        cnt++;
      }
 
      dp[i][0] = cnt;
    } else {
      dp[i][0] = 0;
 
      let cnt = 0;
      let x = arr[i];
 
      while (x % 2 !== 0) {
        x = x / 2;
        cnt++;
      }
 
      dp[i][1] = cnt;
    }
  }
 
  let ans1 = 0;
  for (let i = 0; i < n; i++) {
    if (i % 2 === 0) {
      ans1 += dp[i][0];
    } else {
      ans1 += dp[i][1];
    }
  }
 
  let ans2 = 0;
  for (let i = 0; i < n; i++) {
    if (i % 2 === 0) {
      ans2 += dp[i][1];
    } else {
      ans2 += dp[i][0];
    }
  }
 
  return Math.min(ans1, ans2);
}
 
let arr = [4, 20, 10, 6, 2];
let n = arr.length;
let steps = convertArray(arr, n);
console.log(steps);

Output
3

Time complexity: O(n*logn)
Auxiliary Space: 0(N*2)


Article Tags :