JavaScript实现维吉尼亚(Vigenere)密码算法实例


Posted in Javascript onNovember 22, 2013

传统加密技术对于当今的网络安全发挥不了大作用,但每一本讲述密码学的书的开头都会率先介绍它们,因为它们是密码学的基础,是密码学的历史。几乎每一本密码学的书在讲述Vigenere密码的章节都会有这么一个《Vigenere代换表》用户讲解Vigenere密码机制:

JavaScript实现维吉尼亚(Vigenere)密码算法实例

加密过程很简单,就是给定密钥字母x和明文字母y,密文字母是位于x行和y列的那个字母。这样就决定了加密一条消息需要与消息一样长的密钥字符串,通常,密钥字符串是密钥词的重复。
以《密码编码学与网络安全——原理与实践》中的例子来作为本文的例子。比如密钥词是deceptive,消息是“we are discovered save yourself”,那么加密过程如下:

deceptivedeceptivedeceptive(密钥字符串)
wearediscoveredsaveyourself(消息)
ZICVTWQNGRZGVTWAVZHCQYGLMGJ(密文)

密文中的第一个字母“Z”是怎么得来的?从Vigenere代换表中,以密钥字符串中的“d”为行,消息中的“w”为列的那个字母就是“Z”了。

使用查表的方式多加密几次就能很轻易地总结出规律:将A~Z以0~25编号,那么加密过程就是,在代换表的第一行中找到消息字母,如“w”,然后向后移动d(即3)次,所得的字母就是密文了。如果数到末位,那么下一次移位就从头(即A)继续。 也就是说,可以将A~Z看成一个环,加密过程就是找定消息字母后,将指针往环的某个特定方向移位,次数就是密钥字母所代表的数字。这其实是一个模26的过程。
扩展一下,以上加密仅能对26个字母进行加密,而且不能区分大小写。但其实英文中除了字母外,还有标点符号,还有空格。如果考虑到大部分英文字符,那么Vigenere代换表将比较大,而且有点浪费空间的嫌疑。如果假设能被加密的字符有N个,如果把这N个字符建成一个环,那么加密过程就是模N的过程,即,C(i)=(K(i)+P(i))modN,其中K、C、P分别代表的是密钥空间、密文空间、消息(明文)空间。
网络上有人用C实现了这个加密算法,几乎都是使用查代换表的方法。虽然可以程序生成代换表,但所生成的代换表太有规律了。以下我用Javascript实现了一次,使用的是模的方法,感觉灵活度更大,占用的空间肯定也更小(时间效率尚未估计)

var Vigenere = {
    _strCpr: 'abcdefghijklmnopqrstuvwxyz_12345 67890.ABCDEFGHIJKLMNOPQRSTUVWXYZ',//可以将此字符串的顺序打乱点,或者添加更多字符
    _strKey: function(strK,str){//生成密钥字符串,strK为密钥,str为明文或者密文
        var lenStrK = strK.length;
        var lenStr = str.length;
        if(lenStrK != lenStr){//如果密钥长度与str不同,则需要生成密钥字符串
            if(lenStrK < lenStr){//如果密钥长度比str短,则以不断重复密钥的方式生成密钥字符串
                while(lenStrK < lenStr){
                    strK = strK + strK;
                    lenStrK = 2 * lenStrK;
                }
            }//此时,密钥字符串的长度大于或等于str长度
            strK = strK.substring(0,lenStr);//将密钥字符串截取为与str等长的字符串
        }
        return strK;
    }
}
Vigenere.lenCpr = Vigenere._strCpr.length;
Vigenere.Encrypt = function(K,P){//加密算法,K为密钥,P为明文
    K = Vigenere._strKey(K,P);
    var lenK = K.length;
    var rlt = '';
    var loop = 0;
    for(loop=0; loop<lenK; loop++){
        var iP = Vigenere._strCpr.indexOf(P.charAt(loop));
        if(iP==-1) return '本算法暂时不能对字符:' + P.charAt(loop) + '进行加密';
        var iK = Vigenere._strCpr.indexOf(K.charAt(loop));
        if(iK==-1) return '密钥中包含非法字符:' + K.charAt(loop);
        var i = (iP + iK) % Vigenere.lenCpr;
        rlt = rlt + Vigenere._strCpr.charAt(i);
    }
    return rlt;    
};
Vigenere.DisEncrypt = function(K,C){
    K = Vigenere._strKey(K,C);
    var lenK = K.length;
    var rlt = '';
    var loop = 0;
    for(loop=0; loop<lenK; loop++){
        var iK = Vigenere._strCpr.indexOf(K.charAt(loop));
        if(iK==-1) return '密钥中包含非法字符:' + K.charAt(loop);        
        var iC = Vigenere._strCpr.indexOf(C.charAt(loop));
        if(iK > iC){
            rlt += Vigenere._strCpr.charAt(iC + Vigenere.lenCpr - iK);
        }
        else{
            rlt += Vigenere._strCpr.charAt(iC - iK);
        }
    }
    return rlt;
};
Javascript 相关文章推荐
JS启动应用程序的一个简单例子
May 11 Javascript
Extjs Ajax 乱码问题解决方案
Apr 15 Javascript
Javascript 实用小技巧
Apr 07 Javascript
Jquery Select操作方法集合脚本之家特别版
May 17 Javascript
jQuery实现鼠标经过图片预览大图效果
Apr 10 Javascript
js实现的标题栏新消息闪烁提示效果
Jun 06 Javascript
jQuery使用$.ajax进行异步刷新的方法(附demo下载)
Dec 04 Javascript
jquery 实现滚动条下拉时无限加载的简单实例
Jun 01 Javascript
AngularJS 文件上传控件 ng-file-upload详解
Jan 13 Javascript
详解promise.then,process.nextTick, setTimeout 以及 setImmediate的执行顺序
Nov 21 Javascript
Node.js API详解之 zlib模块用法分析
May 19 Javascript
JS模拟实现京东快递单号查询
Nov 30 Javascript
利用js判断浏览器类型(是否为IE,Firefox,Opera浏览器)
Nov 22 #Javascript
javascript删除option选项的多种方法总结
Nov 22 #Javascript
js截取固定长度的中英文字符的简单实例
Nov 22 #Javascript
String.prototype实现的一些javascript函数介绍
Nov 22 #Javascript
nodeType属性返回被选节点的节点类型介绍
Nov 22 #Javascript
在Iframe中获取父窗口中表单的值(示例代码)
Nov 22 #Javascript
解析URI与URL之间的区别与联系
Nov 22 #Javascript
You might like
php引用计数器进行垃圾收集机制介绍
2012/09/19 PHP
php curl中gzip的压缩性能测试实例分析
2016/11/08 PHP
Yii框架Session与Cookie使用方法示例
2019/10/14 PHP
Yii框架应用组件用法实例分析
2020/05/15 PHP
设置下载不需要倒计时cookie(倒计时代码)
2008/11/19 Javascript
两个select之间option的互相添加操作(jquery实现)
2009/11/12 Javascript
jQuery 动态云标签插件
2014/11/11 Javascript
node.js中的console.log方法使用说明
2014/12/09 Javascript
分享一则javascript 调试技巧
2015/01/02 Javascript
jQuery实现输入框下拉列表树插件特效代码分享
2015/08/27 Javascript
AngularJs动态加载模块和依赖注入详解
2016/01/11 Javascript
实例讲解使用原生JavaScript处理AJAX请求的方法
2016/05/10 Javascript
JS封装的三级联动菜单(使用时只需要一行js代码)
2016/10/24 Javascript
从零学习node.js之利用express搭建简易论坛(七)
2017/02/25 Javascript
Bootstrap实现的经典栅格布局效果实例【附demo源码】
2017/03/30 Javascript
AngularJS的ng-click传参的方法
2017/06/19 Javascript
layui问题之模拟select点击事件的实例讲解
2018/08/15 Javascript
微信小程序和H5页面间相互跳转代码实例
2019/09/19 Javascript
layui多图上传实现删除功能的例子
2019/09/23 Javascript
python获取代码运行时间的实例代码
2018/06/11 Python
Selenium鼠标与键盘事件常用操作方法示例
2018/08/13 Python
pyQT5 实现窗体之间传值的示例
2019/06/20 Python
python统计字符的个数代码实例
2020/02/07 Python
解决Pycharm中恢复被exclude的项目问题(pycharm source root)
2020/02/14 Python
Django如何使用asyncio协程和ThreadPoolExecutor多线程
2020/10/12 Python
如何利用Python matplotlib绘制雷达图
2020/12/21 Python
html5 拖拽及用 js 实现拖拽功能的示例代码
2020/10/23 HTML / CSS
事业单位人员的自我评价范文
2014/09/21 职场文书
党员思想汇报材料
2014/12/19 职场文书
英语感谢信范文
2015/01/20 职场文书
欠条范文
2015/07/03 职场文书
详解JAVA中的OPTIONAL
2021/06/14 Java/Android
Mysql binlog日志文件过大的解决
2021/10/05 MySQL
浅析python中特殊文件和特殊函数
2022/02/24 Python
MySQL数据库如何给表设置约束详解
2022/03/13 MySQL
golang生成vcf通讯录格式文件详情
2022/03/25 Golang