java - 给定一个数字 n,列出所有 n 位数字,使得每个数字都没有重复数字

标签 java c algorithm combinations permutation

我正在尝试解决以下问题。给定一个整数 n,列出所有 n 位数字,使得每个数字都没有重复数字。

例如n为4,则输出如下:

0123
0124
0125
...
9875
9876
Total number of 4-digit numbers is 5040

我目前的方法是蛮力。我可以生成所有 n 位数字,然后使用 Set 列出所有没有重复数字的数字。不过,我很确定有一种更快、更好、更优雅的方法可以做到这一点。

我用 Java 编程,但我可以用 C 阅读源代码。

谢谢

最佳答案

从数学上讲,第一个数字有 10 个选项,第二个有 9 个,第三个有 8 个,7 个 第四次。所以,10 * 9 * 8 * 7 = 5040

以编程方式,您可以使用一些组合逻辑生成这些。使用函数式方法通常可以使代码更简洁;这意味着递归地构建一个新字符串,而不是尝试使用 StringBuilder 或数组来不断修改现有字符串。

示例代码

以下代码将生成排列,无需重复使用数字,无需任何额外的集合或映射等。

public class LockerNumberNoRepeats {
    public static void main(String[] args) {
        System.out.println("Total combinations = " + permutations(4));
    }

    public static int permutations(int targetLength) {
        return permutations("", "0123456789", targetLength);
    }

    private static int permutations(String c, String r, int targetLength) {
        if (c.length() == targetLength) {
            System.out.println(c);
            return 1;
        }

        int sum = 0;
        for (int i = 0; i < r.length(); ++i) {
            sum += permutations(c + r.charAt(i), r.substring(0,i) + r.substring(i + 1), targetLength);
        }
        return sum;
    }
}

输出:

...
9875
9876
Total combinations = 5040

解释

从 @Rick 的评论中提取这个,因为它说得很好,有助于澄清解决方案。

So to explain what is happening here - it's recursing a function which takes three parameters: a list of digits we've already used (the string we're building - c), a list of digits we haven't used yet (the string r) and the target depth or length. Then when a digit is used, it is added to c and removed from r for subsequent recursive calls, so you don't need to check if it is already used, because you only pass in those which haven't already been used.

关于java - 给定一个数字 n,列出所有 n 位数字,使得每个数字都没有重复数字,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52087831/

相关文章:

java - 是否可以将 0001 存储在 int 中?

java - 如果我有一个需要文件路径的构造函数,如果它被打包到一个 jar 中,我怎么能 "fake"呢?

java 字符串替换方法有效但 replaceAll 抛出错误

algorithm - O(nk(log(k))) 算法是否与 O(n(log(k))) 相同

java - 我需要的任务的有效解决方案

在Eclipse中从本地导入git项目的Java代码

c - 需要在 C 中使用 mod 输出分钟数方面的帮助吗?

c - 这行简单的 C 代码如何工作?

c - 有效地从字符串中提取标记

algorithm - 如何找到所有重叠区间的总重量?