维吉尼亚加密

古典密码,属于多表加密。

  • 怎么就是多表了?
    维吉尼亚密码的加密算法实质是凯撒密码,因为他是先分好小组,然后用密钥串对应着分好组的每一个字母进行加密(因为一个凯撒表用密钥串的一个字母加密),当然是遵循下标相同的,比如秘钥为:abc,明文为qwer,然后明文可分组为qwe, r
    然后加密就是不断迭代密钥和明文组,q对应密钥a,然后w对应密钥b,然后明文e对应密钥c,然后第一组遍历完了继续第二组,r对应密钥a,然后加密完成。注意这里即使不够分组也是照样加密,每组加密完成后密钥从头开始遍历

  • 属于分组加密算法
    按照密钥长度进行分组,但是每组字母都不是来自连续的明文或者密文
    我们在分组之前要按照每一个密钥长度为一组,然后每一组的第一个为密钥第一个字母所加密,也就是凯撒加密。
    如图:
    密钥采用五个的字母: JANET
    很明显就是将给出的信息,首先按照原来的顺序按照密钥长度5个分开,然后再根据每一个组的相同下标的字母给与之对应下标的密钥字母进行凯撒加密,比如每一小组的第一个组成的凯撒加密表就是用J加密的,因为秘钥中的第一个字母就是J,然后我们要在分好的小组里面全部的小组第一个都用J加密


  • 密钥是一串字母
    加密要将密钥转换为数字,因此就变成了每一组由密钥中每一个字母进行加密,所以就变成了多个凯撒密码加密,由此得来多表加密。
    就好比分好组排好队之后每一个表去密钥串中领取自己对应组好的密钥(组号就是密钥的下标,每一个秘钥字母对应一个凯撒加密表)

加密算法

  • 在这里采用查表的方式加密,事先生成一个26×26的凯撒的加密表,如图。
    声明:其实这里可以采用传统的凯撒加密方式就是一个一个的移动,我这里之所以采用查表的方式首先是因为书本是这么写的,老师是这么教的,为何要查表我的理解是因为维吉尼亚加密算法是用于文本加密,字母很多的那种,如果我们采用一个个移动的话速度会大大减慢,但是我们事先有了这么一个二维表只需要使用下标即可,而且这个表设计的非常巧妙,无论你纵横怎么看都可以进行加密,因为我们凯撒是明文+密钥,所以比如这里的我们看横排a,然后用纵排的c加密,那么我得到的就是c,你也可以只用使用(a,c)进行查表。(同理解密表也用这个)

    • 生成加解密表

      • 这里的np是要下载numpy包
    def generate_Dit():
    p = 26
    # 生成Vigenere表
    Cipher_list = []
    for row in range(p):
    for column in range(p):
    Cipher_list.append((row + column) % p) Cipher_list = np.asarray(Cipher_list) # 转为矩阵
    # reshape成26*26矩阵,也即Vigenere表
    Cipher_list = Cipher_list.reshape(p, p)
    return Cipher_list # 返回Vigenere表
    • 开始加密

      • 分组打包
      • 加密的时候采用二层循环进行加密
        因为已经分好组了,只需要将每组分别取出,然后采用对应下标与密钥进行对应的凯撒加密即可(这里需要注意的是,我是采用了分好组的下标,所以我只需要取出每组然后再对每组进行循环,而第二层循环的下标我直接给到Key使用,这样保证了不会因为不够一组的数量而导致下标越界,毕竟我遍历的是分好的组,取出该组长度进行遍历,作为key下标,而不是遍历key,因为有的人会采用遍历key的方式给每一个明文加密,我这里用了自己的方法),拿到了密钥与密文就直接到26×26中查表即可,这个表已经写好了一个函数,直接调用即可。
    def enCode():
    saveMess = []
    key = 'cipher' #密钥
    n = len(key)
    tempch = [''] * n #用来开辟空间,然后转储给其他变量
    count = 0 #计数器,防止分组出现不够然后需要将最后剩余的一并添加进去
    for ch in mess:
    if ord('A') <= ord(ch) <= ord('Z') \
    or ord('a') <= ord(ch) <= ord('z'):
    # 确保了只能是字母才能添加进去
    tempch[count % n] = ch
    # count计数器,但是为了与分组数一致要%每组字母数
    count += 1
    if count % n == 0 and count != 0:
    saveMess.append(tempch[0:n + 1]) # 使用切片进行
    tempch = [''] * n
    if count % n != 0: # 将最后剩下的也打包成一组
    saveMess.append(tempch[0:(count % n)])
    # 使用切片将最后一部分单开成一组出来添加 print(saveMess) # 加密
    for ch in saveMess:
    for index in range(len(ch)): # 每一组单独加密
    k = ord(key[index].upper()) - ord('A')
    # 每一个密钥都对应一个ch明文字母
    s = ord(ch[index].upper()) - ord('A')
    self.cipher.append(Cipher_list[k, s]) # 输出
    for num in self.cipher:
    ch = chr(num + ord('A'))
    self.message += ch

解密算法

解密没什么好说的,会了加密解密就是减法的过程,因为维吉尼亚就是查表加密的凯撒密码

  • 分组打包
  • 对应密钥解密
def deCode()
# 分组打包
saveCipher = []
key = 'cipher' #密钥
n = len(key)
tempch = [''] * n
count = 0
for ch in cipher:
if ord('A') <= ord(ch) <= ord('Z') \
or ord('a') <= ord(ch) <= ord('z'):
# 确保了只能是字母才能添加进去
tempch[count % n] = ch
# count计数器,但是为了与分组数一致要%每组字母数
count += 1
if count % n == 0 and count != 0:
saveCipher.append(tempch[0:n + 1]) # 使用切片进行
tempch = [''] * n
if count % n != 0: # 将最后剩下的也打包成一组
saveCipher.append(tempch[0:(count % n)])
# 使用切片将最后一部分单开成一组出来添加 # 解码
deCipher = []
for ch in saveCipher:
for index in range(len(ch)): # 每一组单独解密
# 行不用找,密钥对应每一行,应该在每一行中找对应密文的列,该列就是明文对应的字母数字
for column in range(p): # 找列
if ord(ch[index].upper()) - ord('A') \
== Cipher_list[(ord(key[index].upper())\
- ord('A')), column]:
# print(ch[index].upper(),'key,列:',ord(key[index].upper()) - ord('A'),column)
deCipher.append(column)
break
# 找到了就退出,继续下一下解密字母而不是再继续next密钥,因为一个密钥对应一个字母 # 输出
message = ''
for num in deCipher:
ch = chr(num + ord('A'))
message += ch
print(message)

注意事项

维吉尼亚加密中比较容易犯错的就是没有将明文按照密钥长度进行分小组,然后用key对应着小组的下标进行加密(所以是多表加密,每一个表就是凯撒密码)

这里我开始有一个误解,就是以为他分好小组之后还需要将其分成每一个组大组然后给每一个密钥的字母进行对应加密,这里我有点过度理解了。到后面真正实现加密解密的时候发现我这里根本就是多此一举,因为我们分号小组之后不可以打乱原本明文或者密文的排序,这里根据密钥长度分小组的意思就是方便我们使用密钥对小组每个字母对应着密钥字母来加密,不然我们也不会说按照密钥长度来分组 ,之后的操作就是双层遍历分好组的列表,然后用每个小组的下标给到对应的秘钥取出来,然后就加密对应的字母即可。

密码学—Vigenere加密Python程序的更多相关文章

  1. 为你的Python程序加密

      在实际的工作中,有时候我们需要部署自己的Python应用,但这时候我们并不希望别人能够看到自己的Python源程序.因此,我们需要为自己的源代码进行加密,Python已经为我们提供了这样一套工作机 ...

  2. 如何给python程序加密

    在实际的工作中,有时候我们需要部署自己的Python应用,但这时候我们并不希望别人能够看到自己的Python源程序.因此,我们需要为自己的源代码进行加密,Python已经为我们提供了这样一套工作机制. ...

  3. 第一章 Python程序语言简介

    第一节 Python概述 1. 什么是Python Python是一种 解释型.面向对象.动态数据类型 的高级程序设计语言.由Guido van Rossum与1989年发明,第一个公开发行版本发行于 ...

  4. Python 开篇及第一个Python程序

    本节内容 python 简单介绍 python 2.x 或者python 3.x python 安装 第一个python程序 一.python简单介绍 python的创始人为吉多.范罗苏姆(Guido ...

  5. 将 Python 程序打包成 .exe 文件

    1.简介 做了一个excel的风控模板,里面含有宏,我用python的第三方xlwings部署到linux后发现,linux环境并不支持xlwings. Python 程序都是脚本的方式,一般是在解析 ...

  6. 运行python程序

    1 在windows下运行python程序 1)从DOS命令行运行python脚本 用python解释器来执行python脚本,在windows下面python解释器是python.exe,我的pyt ...

  7. 【python之路2】CMD中执行python程序中文显示乱码

    在IDLE中执行下面代码,中文显示正常: # -*- coding:utf-8 -*- st=raw_input("请输入内容")print st 但在CMD中执行e:\hello ...

  8. Python程序高效地调试

    现在我在debug python程序就只是简单在有可能错误的地方print出来看一下,不知道python有没像c++的一些IDE一样有单步调试这类的工具?或者说各位python大神一般是怎么debug ...

  9. python学习笔记-python程序运行

    小白初学python,写下自己的一些想法.大神请忽略. 安装python编辑器,并配置环境(见http://www.cnblogs.com/lynn-li/p/5885001.html中 python ...

  10. python程序一直在后台运行的解决办法

    刚写了个python程序,要一直在后台运行,即使断开ssh进程也在,下面是解决办法: 假如Python程序为test.py 编写shell脚本start.sh #!/bin/bash python t ...

随机推荐

  1. #团,构造#洛谷 3524 [POI2011]IMP-Party

    题目 有一个 \(3n\) 个点的无向图,保证有一个大小为 \(2n\) 的团,输出一个大小为 \(n\) 的团 分析 每次选择两个不相连的点删掉,那么剩下的 \(n\) 个点一定是团, 因为每次至少 ...

  2. flutter系列之:按比例缩放的AspectRatio和FractionallySizedBox

    目录 简介 AspectRatio FractionallySizedBox 总结 简介 我们在构建UI的时候,为了适应不同的屏幕大小,通常需要进行一些自适应的配置,而最常见的自适应就是根据某个宽度或 ...

  3. 如何通过 Makefile 优化加速编译过程提高开发效率

    在软件开发中,编译是一个必不可少的过程.但是,当代码规模变得越来越大时,编译时间也会变得越来越长,这会严重影响开发效率.在这种情况下,优化Makefile可以帮助我们加速编译过程,以下是一些Makef ...

  4. SQL HAVING 子句详解:在 GROUP BY 中更灵活的条件筛选

    SQL HAVING子句 HAVING子句被添加到SQL中,因为WHERE关键字不能与聚合函数一起使用. HAVING语法 SELECT column_name(s) FROM table_name ...

  5. MySQL 数据库查询与数据操作:使用 ORDER BY 排序和 DELETE 删除记录

    使用 ORDER BY 进行排序 使用 ORDER BY 语句按升序或降序对结果进行排序. ORDER BY 关键字默认按升序排序.要按降序排序结果,使用 DESC 关键字. 示例按名称按字母顺序排序 ...

  6. 优先队列的基本实现【数据结构与算法—TypeScript 实现】

    笔记整理自 coderwhy 『TypeScript 高阶数据结构与算法』课程 特性 效率比普通队列高 每个出队元素拥有最高优先级 可以用 数组.链表 等数据结构实现,但是 堆结构 是最常用的实现方式 ...

  7. spring boot 手动value和自动注入配置的区别[五]

    前言 前面两篇中,写道我们注入配置的方式,是通过是注解的方式完成,如下: @ConfigurationProperties(prefix ="person") 这意味着: 我们写一 ...

  8. K8s集群nginx-ingress监控告警最佳实践

    本文分享自华为云社区<K8s集群nginx-ingress监控告警最佳实践>,作者:可以交个朋友. 一 背景 nginx-ingress作为K8s集群中的关键组成部分.主要负责k8s集群中 ...

  9. 大数据ETL开发之图解Kettle工具入门到精通(经典转载)

    大数据ETL开发之图解Kettle工具(入门到精通) 置顶 袁袁袁袁满 文章目录 第0章 ETL简介 第1章 Kettle简介 1.1 Kettle是什么 1.2 Kettle的两种设计 1.3 Ke ...

  10. 力扣607(MySQL)-销售员(简单)

    题目: 表: SalesPerson 表: Company 表: Orders 编写一个SQL查询,报告没有任何与名为 "RED" 的公司相关的订单的所有销售人员的姓名. 以 任意 ...