使用修改后的 Vigenere 密码算法,解密不会导致原始输入 [关闭]

Posted

技术标签:

【中文标题】使用修改后的 Vigenere 密码算法,解密不会导致原始输入 [关闭]【英文标题】:Using a modified Vigenere cipher algorithm, decryption does not result in original input [closed] 【发布时间】:2015-07-02 08:36:04 【问题描述】:

我已经修改了 Vigenere 密码算法,但是我遇到了问题。如果我加密一个String,然后解密结果,我就不会得到我原来的String。我的源代码:

public class ViganereEncryptionBase64 

    private char[] keys = new char[19];

    int sizeKey = 0;
    int cimin = 0;

    final String MVEAs = " !\"#$%&'()=+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\\]^_'abcdefghijklmnopqrstuvwxyz|~";

    public ViganereEncryptionBase64() 
        String keys = "bangdollaMC08ITATS";
        this.keys = keys.toCharArray();
    

    public String encrypt(String toEncrypt) 
        char charsToEncrypt[] = toEncrypt.toCharArray();
        char encryptedChars[] = toEncrypt.toCharArray();
        int i = 0;
        while (i < encryptedChars.length) 

            int sube = MVEAs.indexOf(charsToEncrypt[i]) + MVEAs.indexOf(keys[sizeKey]) + cimin;

            sizeKey++;
            if (sizeKey == keys.length)
                sizeKey = 0;

            encryptedChars[i] = MVEAs.charAt(Math.floorMod(sube, 95));
            cimin = MVEAs.indexOf(encryptedChars[i]);
            i += 1;
        
        return String.valueOf(encryptedChars);
    

    public String decrypt(String toDecrypt) 
        char charsToDecrypt[] = toDecrypt.toCharArray();
        char decryptedChars[] = toDecrypt.toCharArray();
        int i = 0;
        while (i < charsToDecrypt.length) 
            int sube = MVEAs.indexOf(charsToDecrypt[i]) - MVEAs.indexOf(keys[sizeKey]) - cimin;

            sizeKey++;
            if (sizeKey == keys.length)
                sizeKey = 0;
            decryptedChars[i] = MVEAs.charAt(Math.floorMod(sube, 95));
            cimin = MVEAs.indexOf(charsToDecrypt[i]);
            i++;
        
        return String.valueOf(decryptedChars);
    

说明问题的用例是

public static void main(String[] args) 
    ViganereEncryptionBase64 viganere = new ViganereEncryptionBase64();
    System.out.println("Result encryption: " + viganere.encrypt("<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">"));
    viganere = new ViganereEncryptionBase64();
    System.out.println("Result description: " + viganere.decrypt("~at,4X~<Cp|\"(>rdnds~1x_\\XTmN5TirX-9DZv+opkhJLbT[x7Mk/'J&|p&A0qAMR_yh9|H#\\Y91/kKtQI,Su3Ik, p$@IH.c:Ue'Lj25X L#[3f8ql3U]oF"));

原始输入是"&lt;!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\"&gt;"

加密后的结果是"~at,4X~&lt;Cp|\"(&gt;rdnds~1x_\\XTmN5TirX-9DZv+opkhJLbT[x7Mk/'J&amp;|p&amp;A0qAMR_yh9|H#\\Y91/kKtQI,Su3Ik, p$@IH.c:Ue'Lj25X L#[3f8ql3U]oF"

然后解密结果为"&lt;!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"&gt;"

这是不同的。

【问题讨论】:

我不确定我是否看到了您的问题,请您更清楚地解释您的问题是什么? @sebastian Troy 我在运行我的应用程序时遇到问题 dihasil word 正确地通过 Dectiption 过程与他在我的结果和我的呼叫方法中的诉求的初始文本不同你可以看到我的问题 可以缩短你的代码,所以唯一的代码就是问题代码? ~at,4X~&lt;Cp|"(&gt;rdnds~1x_\XTmN5TirX-9DZv+opkhJLbT[x7Mk/'J&amp;|p&amp;A0qAMR_yh9|H#\Y91/kKtQI,Su3Ik, p$@IH.c:Ue'Lj25X L#[3f8ql3U]oF 有点长而且令人困惑。此外,您的英语有点支离破碎,因此很难确定确切的问题。我知道一些输入与输出不匹配,但究竟什么不匹配仍然很难解决。 这就是“我知道某些输入与输出不匹配”我尝试我已经尝试替换他的纯文本但仍然喜欢它也许你可以帮助我我为我的英语非常糟糕而道歉 我没有看到您的输入和输出之间的差异...'\' 反斜杠字符存在差异,但那是因为它们被用作 escape sequences。这能回答你的问题吗? 【参考方案1】:

所以你的加密和解密工作完美,我已经运行了你的代码,没有看到任何测试输入和输出之间有任何区别。

如果我们使用不需要转义序列的示例,我认为您可能会对the backslashes \ being used as escape characters 感到困惑:

public static void main(String[] args) 
    viganere = new ViganereEncryptionBase64();
    System.out.println("Result encryption: " + viganere.encrypt("Hello!"));
    // Which is encrypted to "+R.b7("

    viganere = new ViganereEncryptionBase64();
    System.out.println("Result description: " + viganere.decrypt("+R.b7("));
    // Which is decrypted to "Hello!"

您可以看到它完美运行。

在您的示例中,每个" 之前都有一个\,这样Java 就不会认为您已经结束了String,您会注意到它允许您使用" 一半通过String 而不结束它。

所以实际上你的String 中仍然有一个\,看起来好像没有,因为System.out.println 不会打印它。所有转义字符都是如此;当打印给用户时,它们将被翻译成标签或新行等

【讨论】:

我想加密一个源代码,它肯定有标点符号,例如“/等” 标点符号使用'\'本身不会有问题,实际上前面的'\'实际上存在于解密的String中,只是System.out.println不会显示它们。我将编辑我的答案以澄清。

以上是关于使用修改后的 Vigenere 密码算法,解密不会导致原始输入 [关闭]的主要内容,如果未能解决你的问题,请参考以下文章

python 简单的加密/解密算法(Vigenere密码)

Java 中的 Vigenere 密码算法 - 将消息解密为明文

尝试加密和解密 vigenere 密码

Python Vigenere 代码重复错误

Vigenere 密码解密问题

用于解密的 Vigenere 密码“字符串索引超出范围”