随机密码生成器返回错误字符-Java

我当前正在使用以下代码生成随机密码:

static public String randomPasswordGenerator(int n,String valid) 
{ 
      char[] pwd = new char[n];
      Random rnd = new Random();
      for (int i = 0; i < pwd.length; i++)
      {
        pwd[i] = valid.charAt(rnd.nextInt(valid.length()));
      }
      return new String(pwd);
}

有效参数当前设置为:

String valid = "abcdefghijkmnopqrstuvwxyzABCDEFGHJKLMNPQRSTUVWXYZ123456789#$&%£";

有时,当我生成密码时,我发现正在生成奇怪的字符,例如,我可以得到:n9iB8Qj6inR(其中最后一个字符不包含在有效集中)

知道为什么会这样吗?

非常感谢

编辑 我虽然与编码问题有关,但是在调试上述函数的返回字符串时,我可以直接看到那个奇怪的字符。 另外,使用字符集作为“#$&%£”有时会返回所有字符以及那个奇怪的A(例如:&%Â&$&#£%#Â)

li3029 回答:随机密码生成器返回错误字符-Java

您粘贴的代码没有错误,应该按照您想要的去做。

尽管如此,这几乎100%肯定是字符编码问题。

有效字符串中的所有字符(以外的井号)都在ASCII范围内32-127,并且在几乎所有现有的字符编码中,这些字符都可以正常工作(字符串“ foo”如果使用ASCII编码为字节,然后使用UTF-8或ISO-8859-1或Win CP252或几乎其他任何东西进行解码,则仍然是“ foo”),但是不是。如果您使用字符串“那将是5英镑,请!”,使用例如ISO-8859-1将其编码为字节,然后使用UTF-8将其解码回字符串,则会得到“就是5,请!”。

因此,暂时推断一下,此字符串是使用一种字符集编码进行编码,然后使用另一种字符集编码进行解码的,这就是您的错误,但是,只要您通过此字符抛出该字符,该错误就不会起作用。越野车过程全都在ASCII表的32-127范围内。

因此,您有两种方法可以解决此问题。要么将其修复:

  1. 确保有效字符列表仅包含ASCII 32-127个字符。例如,删除英镑,使其为负号,下划线或圆括号。

  2. 找到将字符串编码为字节的位置,反之亦然,并确保您始终明确地说出正在使用的编码。然后,我强烈建议您明确实施UTF-8。例如:

坏:

new FileReader(new File("/path/to/a/file"))
byte[] bytes = .... some bytes ...; String x = new String(bytes);

好:

Files.newBufferedReader(Paths.get("/path/to/a/file")) // case 1
new BufferedReader(new InputStreamReader(new FileInputStream(new File("/path/to/a/file")),StandardCharsets.UTF_8)); // case 2
byte[] bytes = .... some bytes ...; String x = new String(bytes,StandardCharsets.UTF_8);

尽管在所有这些情况下都需要注意,但是您应该使用try-with-resources来正确关闭它们。

案例1很好,因为与Java核心库中的大多数其他地方不同,Files API被定义为始终使用UTF-8作为编码(而其他地方都使用“平台默认值”,无论可能通常,这是一个不好的选择),情况2和情况3很好,因为您明确使用了UTF-8。

本文链接:https://www.f2er.com/3167395.html

大家都在问