📌  相关文章
📜  前 N 个自然数的字典序最大数组,使得每个重复出现的距离等于它与前一次出现的值的距离

📅  最后修改于: 2021-10-28 01:41:27             🧑  作者: Mango

给定一个正整数N,则任务是构建字典顺序最大尺寸(2 * N – 1)的阵列,其包括第一N的自然数,使得每个元件除1出现两次并且X的重复正是X的距离间隔在构造的数组。

例子:

方法:这个问题可以使用回溯解决。这个想法是根据给定条件生成所有可能的排列并打印满足给定条件的排列。请按照以下步骤解决问题:

  • 初始化一个数组,比如ans[] ,每个索引的大小为(2*N – 1) 0 s 和一个 HashMap 来存储分配给构造数组的所有元素。
  • 定义一个函数constructedArray(i, N)以通过执行以下步骤生成结果数组:
    • 如果i 的值为(2*N – 1) ,则生成可能的排列之一。因此,返回true
    • 否则,如果当前索引处的值已经分配,则递归调用下一次迭代constructArray(i+1, N)
    • 否则,执行以下操作:
      • 放置从范围内的每个未访问号码[1,N]:N开始。
      • 如果在上述步骤中选择的值不会导致数组的可能组合,则从数组中删除当前值并通过分配范围中的其他元素来尝试其他可能的组合。
      • 如果没有获得可能的组合,则返回false
  • 完成上述步骤后,打印得到的数组ans[]

下面是上述方法的实现:

C++
// C++14 program to implement
// the above approach
#include 
using namespace std;
const int N = 4;
  
// Stores the required sequence
vector ans(2 * N - 1, 0);
  
// Stores the visited and unvisited values
set visited;
  
// Function to construct the array
// according to the given conditions
bool constructArray(int i)
{
    
    // Base Case
    if (i == ans.size()) {
        return true;
    }
  
    // If a value is already assigned
    // at current index, then recursively
    // call for the next index
    if (ans[i] != 0)
        return constructArray(i + 1);
  
    else {
  
        // Iterate over the range[N, 1]
        for (int val = N; val >= 1; val--) {
  
            // If the current value is
            // already visited, continue
            if (visited.find(val) != visited.end())
                continue;
  
            // Otherwise, mark this value as
            // visited and set ans[i] = val
            visited.insert(val);
            ans[i] = val;
  
            // If val is equal to 1, then
            // recursively call for the
            // next index
            if (val == 1) {
                bool found = constructArray(i + 1);
  
                // If solution is found,
                // then return true
                if (found)
                    return true;
            }
  
            // For all other values, assign
            // ans[i + val] to val if the
            // i + val < ans.length
            else if (i + val < ans.size()
                     && ans[i + val] == 0) {
                ans[val + i] = val;
  
                // Recursively call for
                // next index to check if
                // solution can be found
                bool found = constructArray(i + 1);
  
                // If solution is found then
                // return true
                if (found)
                    return true;
  
                // BackTracking step
                ans[i + val] = 0;
            }
  
            // BackTracking step
            ans[i] = 0;
            visited.erase(val);
        }
    }
  
    // In all other cases, return false
    return false;
}
  
// Driver code
int main()
{
    
    // Function Call
    constructArray(0);
  
    // Print the resultant array
    for (int X : ans)
        cout << X << " ";
    return 0;
}
  
// This code is contributed by kingash.


Java
// Java program for the above approach
import java.io.*;
import java.util.*;
  
class GFG {
  
    // Stores the required sequence
    static int ans[];
  
    // Stores the visited and unvisited values
    static HashSet visited;
  
    // Function to construct the array
    // according to the given conditions
    public static boolean
    constructArray(int i, int N)
    {
  
        // Base Case
        if (i == ans.length) {
            return true;
        }
  
        // If a value is already assigned
        // at current index, then recursively
        // call for the next index
        if (ans[i] != 0)
            return constructArray(i + 1, N);
  
        else {
  
            // Iterate over the range[N, 1]
            for (int val = N; val >= 1; val--) {
  
                // If the current value is
                // already visited, continue
                if (visited.contains(val))
                    continue;
  
                // Otherwise, mark this value as
                // visited and set ans[i] = val
                visited.add(val);
                ans[i] = val;
  
                // If val is equal to 1, then
                // recursively call for the
                // next index
                if (val == 1) {
                    boolean found
                        = constructArray(i + 1, N);
  
                    // If solution is found,
                    // then return true
                    if (found)
                        return true;
                }
  
                // For all other values, assign
                // ans[i + val] to val if the
                // i + val < ans.length
                else if (i + val < ans.length
                         && ans[i + val] == 0) {
                    ans[val + i] = val;
  
                    // Recursively call for
                    // next index to check if
                    // solution can be found
                    boolean found
                        = constructArray(i + 1, N);
  
                    // If solution is found then
                    // return true
                    if (found)
                        return true;
  
                    // BackTracking step
                    ans[i + val] = 0;
                }
  
                // BackTracking step
                ans[i] = 0;
                visited.remove(val);
            }
        }
  
        // In all other cases, return false
        return false;
    }
  
    // Driver Code
    public static void main(String[] args)
    {
        int N = 4;
  
        ans = new int[2 * N - 1];
        visited = new HashSet<>();
  
        // Function Call
        constructArray(0, N);
  
        // Print the resultant array
        for (int X : ans)
            System.out.print(X + " ");
    }
}


Python3
# Python3 program for the above approach
  
# Function to construct the array
# according to the given conditions
def constructArray(i, N):
    global ans, visited
  
    # Base Case
    if (i == len(ans)):
        return True
      
    # If a value is already assigned
    # at current index, then recursively
    # call for the next index
    if (ans[i] != 0):
        return constructArray(i + 1, N)
    else:
  
        # Iterate over the range[N, 1]
        for val in range(N, 0, -1):
  
            # If the current value is
            # already visited, continue
            if (val in visited):
                continue
  
            # Otherwise, mark this value as
            # visited and set ans[i] = val
            visited[val] = 1
            ans[i] = val
  
            # If val is equal to 1, then
            # recursively call for the
            # next index
            if (val == 1):
                found = constructArray(i + 1, N)
  
                # If solution is found,
                # then return true
                if (found):
                    return True
  
            # For all other values, assign
            # ans[i + val] to val if the
            # i + val < ans.length
            elif (i + val < len(ans) and ans[i + val] == 0):
                ans[val + i] = val
  
                # Recursively call for
                # next index to check if
                # solution can be found
                found = constructArray(i + 1, N)
  
                # If solution is found then
                # return true
                if (found):
                    return True
  
                # BackTracking step
                ans[i + val] = 0
  
            # BackTracking step
            ans[i] = 0
            del visited[val]
  
    # In all other cases, return false
    return False
  
# Driver Code
if __name__ == '__main__':
    N = 4
    ans = [0]*(2 * N - 1)
    visited = {}
  
    # Function Call
    constructArray(0, N)
  
    # Print the resultant array
    for x in ans:
        print(x,end=" ")
  
        # this code is contributed by mohit kumar 29.


C#
// C# program for the above approach
using System;
using System.Collections.Generic;
using System.Linq;
  
class GFG{
  
  // Stores the required sequence
  static int[] ans;
  
  // Stores the visited and unvisited values
  static HashSet visited;
  
  // Function to construct the array
  // according to the given conditions
  public static bool
    constructArray(int i, int N)
  {
  
    // Base Case
    if (i == ans.Length) {
      return true;
    }
  
    // If a value is already assigned
    // at current index, then recursively
    // call for the next index
    if (ans[i] != 0)
      return constructArray(i + 1, N);
  
    else {
  
      // Iterate over the range[N, 1]
      for (int val = N; val >= 1; val--) {
  
        // If the current value is
        // already visited, continue
        if (visited.Contains(val))
          continue;
  
        // Otherwise, mark this value as
        // visited and set ans[i] = val
        visited.Add(val);
        ans[i] = val;
  
        // If val is equal to 1, then
        // recursively call for the
        // next index
        if (val == 1) {
          bool found
            = constructArray(i + 1, N);
  
          // If solution is found,
          // then return true
          if (found)
            return true;
        }
  
        // For all other values, assign
        // ans[i + val] to val if the
        // i + val < ans.length
        else if (i + val < ans.Length
                 && ans[i + val] == 0) {
          ans[val + i] = val;
  
          // Recursively call for
          // next index to check if
          // solution can be found
          bool found
            = constructArray(i + 1, N);
  
          // If solution is found then
          // return true
          if (found)
            return true;
  
          // BackTracking step
          ans[i + val] = 0;
        }
  
        // BackTracking step
        ans[i] = 0;
        visited.Remove(val);
      }
    }
  
    // In all other cases, return false
    return false;
  }
  
  // Driver Code
  static public void Main()
  {
    int N = 4;
  
    ans = new int[2 * N - 1];
    visited = new HashSet();
  
    // Function Call
    constructArray(0, N);
  
    // Print the resultant array
    foreach (int X in ans)
      Console.Write(X + " ");
  }
}
  
// This code is contributed by code_hunt.


Javascript


输出:
4 2 3 2 4 3 1

时间复杂度: O(N!)
辅助空间: O(N)

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