我正在经历Euler项目Problem 059。
如何从that textfile的解密可能性中找到有效消息?
将输入转换为数组后,使用三个字母的键执行XOR并将结果强制转换(char),所有消息都无法通过isLegible检查。
try {
// Read the contents of the provided text file
// and convert them into an int[] array of encrypted ASCII codes
Scanner fileRead = new Scanner(new File("p059_cipher.txt"));
StringBuilder input = new StringBuilder();
while (fileRead.hasNext()) {
input.append(fileRead.next());
}
String[] parts = input.toString().split("[,]");
int[] elements = new int[parts.length];
for (int i = 0; i < parts.length; i++)
elements[i] = Integer.parseInt(parts[i]);
char[] key;
char[] convertedParts;
// Loop through possible keys,
// from ['a', 'a', 'a'] to ['z', 'z', 'z']
for (char lc1 = 'a'; lc1 <= 'z'; lc1++) {
for (char lc2 = 'a'; lc2 <= 'z'; lc2++) {
for (char lc3 = 'a'; lc3 <= 'z'; lc3++) {
key = new char[]{lc1, lc2, lc3};
// XOR each of the ASCII code chars,
// using the appropriate key letter
convertedParts = new char[elements.length];
for (int done = 0; done < elements.length; done++) {
convertedParts[done] =
(char) (elements[done] ^ key[done%3]);
}
// If the decrypted message counts as an answer,
// print out the sum of ASCII values
// of decrypted characters
if (isLegible(convertedParts))
System.out.println(getAsciiSum(convertedParts));
}
}
}
} catch (java.io.FileNotFoundException e) {
e.printStackTrace();
}
}
// Check whether or not the decoded message
// consists only of valid characters
private static boolean isLegible(char[] characters) {
// 32-34: SPACE, '!', '"'
// 40-41: '(', ')'
// 44-46: '.', '-', ','
// 48-59: '0'-'9', ':', ';'
// 63: '?'
// 65-90: 'A'-'Z'
for (char character : characters) {
int value = (int) character;
if ( ! ( (value >= 32 && value <= 34)
|| (value >= 40 && value <= 41)
|| (value >= 44 && value <= 46)
|| (value >= 48 && value <= 59)
|| (value == 63)
|| (value >= 65 && value <= 90) ) ) {
return false;
}
}
return true;
}
// Sums up the ASCII values of characters
private static long getAsciiSum(char[] characters) {
long sum = 0;
for (char character : characters)
sum += (int)(character);
return sum;
}
我希望输出内容清晰易懂,但在循环进行解密时找不到任何内容。