Generate a permutation of first N natural numbers having count of unique adjacent differences equal to K | Set 2

• Last Updated : 10 Dec, 2021

Given two positive integers N and K, the task is to construct a permutation of the first N natural numbers such that all possible absolute differences between adjacent elements are K.

Examples:

Input: N = 3, K = 1
Output: 1 2 3
Explanation: Considering the permutation {1, 2, 3}, all possible unique absolute difference of adjacent elements is {1}. Since the count is 1(= K), print the sequence {1, 2, 3} as the resultant permutation.

Input: N = 3, K = 2
Output: 1 3 2

The naive approach and the two-pointer approach of this problem are already discussed here. This article discusses a different approach deque.

Approach: It is easy to see that, answers for all values of K between [1, N-1] can be generated. For any K outside this range, there exists no answer. To solve the problem maintain a double-ended queue for all the current elements and a vector to store the sequence. Also, maintain a boolean value that will help to determine to pop the front or back element. Iterate the remaining element and if K is greater than 1 then push the element according to the boolean value and decrease K by 1. Flip the boolean value so that all remaining differences will have value 1. Follow the steps below to solve the problem:

Below is the implementation of the above approach.

C++

 // C++ Program for the above approach#include using namespace std; // Function to calculate the required arrayvoid K_ValuesArray(int N, int K){     // Check for base cases    if (K < 1 || K >= N) {        cout << -1;        return;    }     // Maintain a deque to store the    // elements from [1, N];    deque dq;    for (int i = 2; i <= N; i++) {        dq.push_back(i);    }     // Maintain a boolean value which will    // tell from where to pop the element    bool front = true;     // Create a vector to store the answer    vector ans;     // Push 1 in the answer initially    ans.push_back(1);     // Push the remaining elements    if (K > 1) {        front ^= 1;        K--;    }     // Iterate over the range    for (int i = 2; i <= N; i++) {        if (front) {            int val = dq.front();            dq.pop_front();             // Push this value in            // the ans vector            ans.push_back(val);            if (K > 1) {                K--;                 // Flip the boolean                // value                front ^= 1;            }        }        else {            int val = dq.back();            dq.pop_back();             // Push value in ans vector            ans.push_back(val);            if (K > 1) {                K--;                 // Flip boolean value                front ^= 1;            }        }    }     // Print Answer    for (int i = 0; i < N; i++) {        cout << ans[i] << " ";    }} // Driver Codeint main(){    int N = 7, K = 1;    K_ValuesArray(N, K);     return 0;}

Java

 // Java Program for the above approachimport java.util.*;class GFG{ // Function to calculate the required arraystatic void K_ValuesArray(int N, int K){     // Check for base cases    if (K < 1 || K >= N) {        System.out.print(-1);        return;    }     // Maintain a deque to store the    // elements from [1, N];    Deque dq = new LinkedList();    for (int i = 2; i <= N; i++) {        dq.add(i);    }     // Maintain a boolean value which will    // tell from where to pop the element    boolean front = true;     // Create a vector to store the answer    Vector ans = new Vector();     // Push 1 in the answer initially    ans.add(1);     // Push the remaining elements    if (K > 1) {        front ^=true;        K--;    }     // Iterate over the range    for (int i = 2; i <= N; i++) {        if (front) {            int val = dq.peek();            dq.removeFirst();             // Push this value in            // the ans vector            ans.add(val);            if (K > 1) {                K--;                 // Flip the boolean                // value                front ^=true;            }        }        else {            int val = dq.getLast();            dq.removeLast();             // Push value in ans vector            ans.add(val);            if (K > 1) {                K--;                 // Flip boolean value                front ^=true;            }        }    }     // Print Answer    for (int i = 0; i < N; i++) {        System.out.print(ans.get(i)+ " ");    }} // Driver Codepublic static void main(String[] args){    int N = 7, K = 1;    K_ValuesArray(N, K); }} // This code is contributed by 29AjayKumar

Python3

 # python Program for the above approachfrom collections import deque # Function to calculate the required arraydef K_ValuesArray(N, K):     # Check for base cases    if (K < 1 or K >= N):        print("-1")        return     # Maintain a deque to store the    # elements from [1, N];    dq = deque()    for i in range(2, N + 1):        dq.append(i)     # Maintain a boolean value which will    # tell from where to pop the element    front = True     # Create a vector to store the answer    ans = []     # Push 1 in the answer initially    ans.append(1)     # Push the remaining elements    if (K > 1):        front ^= 1        K -= 1     # Iterate over the range    for i in range(2, N+1):        if (front):            val = dq.popleft()             # Push this value in            # the ans vector            ans.append(val)            if (K > 1):                K -= 1                 # Flip the boolean                # value                front ^= 1         else:            val = dq.pop()             # Push value in ans vector            ans.append(val)            if (K > 1):                K -= 1                 # Flip boolean value                front ^= 1     # Print Answer    for i in range(0, N):        print(ans[i], end=" ") # Driver Codeif __name__ == "__main__":     N = 7    K = 1    K_ValuesArray(N, K)     # This code is contributed by rakeshsahni

C#

 // C# Program for the above approach using System;using System.Collections.Generic;class GFG{     // Function to calculate the required array    static void K_ValuesArray(int N, int K)    {         // Check for base cases        if (K < 1 || K >= N)        {            Console.Write(-1);            return;        }         // Maintain a deque to store the        // elements from [1, N];        LinkedList dq = new LinkedList();        for (int i = 2; i <= N; i++)        {            dq.AddLast(i);        }         // Maintain a boolean value which will        // tell from where to pop the element        bool front = true;         // Create a vector to store the answer        List ans = new List();         // Push 1 in the answer initially        ans.Add(1);         // Push the remaining elements        if (K > 1)        {            front ^= true;            K--;        }         // Iterate over the range        for (int i = 2; i <= N; i++)        {            if (front)            {                int val = dq.First.Value;                dq.RemoveFirst();                 // Push this value in                // the ans vector                ans.Add(val);                if (K > 1)                {                    K--;                     // Flip the boolean                    // value                    front ^= true;                }            }            else            {                int val = dq.Last.Value;                dq.RemoveLast();                 // Push value in ans vector                ans.Add(val);                if (K > 1)                {                    K--;                     // Flip boolean value                    front ^= true;                }            }        }         // Print Answer        for (int i = 0; i < N; i++)        {            Console.Write(ans[i] + " ");        }    }     // Driver Code    public static void Main()    {        int N = 7, K = 1;        K_ValuesArray(N, K);     }} // This code is contributed by Saurabh Jaiswal

Javascript


Output
1 2 3 4 5 6 7

Time Complexity: O(N)
Auxiliary Space: O(N)

My Personal Notes arrow_drop_up