所以我正在制作一个Caesar密码程序我加密工作正常,这是我遇到问题的解密。
以下是适用于大写字母加密的代码:
if (isupper(p[i])){
char c = ((p[i] - 'A') + k % 26) + 'A';
}
现在我认为解密会是:
if (isupper(pp[i])){
char c = (abs((p[i] - 'A') - k) % 26) + 'A';
}
我遇到的问题是,如果k = 1并且p [i] ='A',它将只输出字母'B'而不是'Z',它不会像它应该这样包围,如果k = 2并且p [i] ='A'它应该输出字母'Y'。如果k = 1并且p [i] ='B'它会输出'A',感谢您的帮助。
答案 0 :(得分:1)
这应该这样做:
if (isupper(p[i])){
char c = (p[i] - 'A' + 26 - k) % 26) + 'A';
}
+ 26
为您提供包装
以这种方式思考(三位数字格式只是为了使事情顺利排列):
| 000 | 001 | 002 | ... | 024 | 025 | plain
| A | B | C | ... | Y | Z |
| 003 | 004 | 005 | ... | 001 | 002 | crypto
现在,认识到
(n + 26) % 26 === (n % 26)
所以:
| 000 | 001 | 002 | ... | 024 | 025 | plain
| A | B | C | ... | Y | Z |
| 029 | 030 | 031 | ... | 053 | 054 | crypto
当你考虑模26时,等同于上面的
这让生活变得更轻松。明文符号集由'A'
到'A' + 25
的连续整数组成。问题是密文符号集不是连续的...... 025
处存在不连续性。通过添加26,您可以将密文转换为从'A' + k + 26
到'A' + k + 49
的连续范围。
更容易将连续的密文符号集映射到您的明文符号集。
由于凯撒代码可能是任一方向的转变而解密只是相反的转变,你可以将其与
结合起来。boolean decrypt;
int k;
...
k = k % 26; // Ensure that the shift doesn't include any wrapping
if(decrypt) {
k *= -1;
}
if (isupper(p[i])){
char c = (p[i] - 'A' + 26 + k) % 26) + 'A';
}
答案 1 :(得分:0)
在加密中,
((p[i] - 'A') + k % 26) + 'A'
考虑将其评估为
t1 = p[i] - 'A'
t2 = k % 26
result = t1 + t2 + 'A'
那可能不是你想要的。解密不会反转该算法,主要是因为额外的分组改变了操作的顺序。
答案 2 :(得分:0)
你没有考虑他们环绕的事实,试试这样:
if ((p[i] - 'A' - k) < 0 )
c = 'Z' - (abs(p[i] - 'A' - k) % 26) + 1;
else
c = (abs(p[i] - 'A' - k) % 26) + 'A';
我认为你也不需要moudulo“%”。