📜  从给定的字符集生成所有密码

📅  最后修改于: 2021-04-24 23:58:53             🧑  作者: Mango

给定一组字符,从中生成所有可能的密码。这意味着我们应该使用给定的字符,重新排列以及达到给定的长度来生成单词的所有可能排列。

例子:

Input : arr[] = {a, b}, 
          len = 2.
Output :
a b aa ab ba bb

解决方案是在给定的字符数组上使用递归。这个想法是首先将所有可能的长度和一个空字符串传递给一个辅助函数。在辅助函数,我们将所有字符一一追加到当前字符串,然后重复填充剩余的字符串,直到达到所需的长度为止。

使用下面的递归树可以更好地可视化它:

(a, b)
         /   \
        a     b
       / \   / \
      aa  ab ba bb

以下是上述方法的实现。

C++
// C++ program to generate all passwords for given characters
#include 
using namespace std;
  
// int cnt;
  
// Recursive helper function, adds/removes characters
// until len is reached
void generate(char* arr, int i, string s, int len)
{
    // base case
    if (i == 0) // when len has been reached
    {
        // print it out
        cout << s << "\n";
        // cnt++;
        return;
    }
  
    // iterate through the array
    for (int j = 0; j < len; j++) {
  
        // Create new string with next character
        // Call generate again until string has
        // reached its len
        string appended = s + arr[j];
        generate(arr, i - 1, appended, len);
    }
  
    return;
}
  
// function to generate all possible passwords
void crack(char* arr, int len)
{
    // call for all required lengths
    for (int i = 1; i <= len; i++) {
        generate(arr, i, "", len);
    }
}
  
// driver function
int main()
{
    char arr[] = { 'a', 'b', 'c' };
    int len = sizeof(arr) / sizeof(arr[0]);
    crack(arr, len);
  
    //cout << cnt << endl;
    return 0;
}
// This code is contributed by Satish Srinivas.


Java
// Java program to generate all passwords for given characters
import java.util.*;
  
class GFG
{
  
    // int cnt;
    // Recursive helper function, adds/removes characters
    // until len is reached
    static void generate(char[] arr, int i, String s, int len)
    {
        // base case
        if (i == 0) // when len has been reached
        {
            // print it out
            System.out.println(s);
              
            // cnt++;
            return;
        }
  
        // iterate through the array
        for (int j = 0; j < len; j++)
        {
  
            // Create new string with next character
            // Call generate again until string has
            // reached its len
            String appended = s + arr[j];
            generate(arr, i - 1, appended, len);
        }
  
        return;
    }
  
    // function to generate all possible passwords
    static void crack(char[] arr, int len)
    {
        // call for all required lengths
        for (int i = 1; i <= len; i++)
        {
            generate(arr, i, "", len);
        }
    }
  
    // Driver code
    public static void main(String[] args)
    {
        char arr[] = {'a', 'b', 'c'};
        int len = arr.length;
        crack(arr, len);
    }
  
}
  
// This code has been contributed by 29AjayKumar


Python 3
# Python3 program to 
# generate all passwords
# for given characters
  
# Recursive helper function, 
# adds/removes characters
# until len is reached
def generate(arr, i, s, len):
  
    # base case
    if (i == 0): # when len has
                 # been reached
      
        # print it out
        print(s)
        return
      
    # iterate through the array
    for j in range(0, len):
  
        # Create new string with 
        # next character Call 
        # generate again until 
        # string has reached its len
        appended = s + arr[j]
        generate(arr, i - 1, appended, len)
  
    return
  
# function to generate 
# all possible passwords
def crack(arr, len):
  
    # call for all required lengths
    for i in range(1 , len + 1): 
        generate(arr, i, "", len)
      
# Driver Code
arr = ['a', 'b', 'c' ]
len = len(arr)
crack(arr, len)
  
# This code is contributed by Smita.


C#
// C# program to generate all passwords for given characters
using System;
      
class GFG
{
  
    // int cnt;
    // Recursive helper function, adds/removes characters
    // until len is reached
    static void generate(char[] arr, int i, String s, int len)
    {
        // base case
        if (i == 0) // when len has been reached
        {
            // print it out
            Console.WriteLine(s);
              
            // cnt++;
            return;
        }
  
        // iterate through the array
        for (int j = 0; j < len; j++)
        {
  
            // Create new string with next character
            // Call generate again until string has
            // reached its len
            String appended = s + arr[j];
            generate(arr, i - 1, appended, len);
        }
  
        return;
    }
  
    // function to generate all possible passwords
    static void crack(char[] arr, int len)
    {
        // call for all required lengths
        for (int i = 1; i <= len; i++)
        {
            generate(arr, i, "", len);
        }
    }
  
    // Driver code
    public static void Main(String[] args)
    {
        char []arr = {'a', 'b', 'c'};
        int len = arr.Length;
        crack(arr, len);
    }
  
}
  
/* This code contributed by PrinciRaj1992 */


输出:

a
b
c
aa
ab
ac
ba
bb
bc
ca
cb
cc
aaa
aab
aac
aba
abb
abc
aca
acb
acc
baa
bab
bac
bba
bbb
bbc
bca
bcb
bcc
caa
cab
cac
cba
cbb
cbc
cca
ccb
ccc

如果要查看单词数,可以取消注释代码中具有cnt变量的行。我们可以观察到结果是 n^1 + n^2 +..+ n^n ,其中n = len。因此程序的时间复杂度也是O(n * n^n) ,因此是指数级的。我们还可以检查特定的密码
同时生成并中断循环并返回(如果找到)。我们还可以包含要生成的其他符号,如果需要,可以通过使用HashTable预处理输入来删除重复项。