Python实现加解密文本文件

1. 实验目的

借助异或操作,实现一个简单的文件加密和解密程序。


2. 实验所用仪器(或实验环境)

Python3.6


3. 实验基本原理及步骤(或方案设计及理论计算)

3.1 实验原理:

  • 任务1:定义生成随机密钥的函数。函数带有一个参数L;函数生成一个包含L个字节的随机字节串(可以借助secrets包中的token_bytes模块实现),并将随机字节串转换成整数返回。
  • 任务2:定义实现加密单元的函数。函数带有一个字符串参数;函数将字符串编码为字节串并转换为整数,然后将它与一个随机密钥进行异或运算生成密文,最后将密文和随机密钥返回。
  • 任务3:定义实现解密单元的函数。函数带有两个参数,分别是任务2中函数返回的密文和密钥。函数将密文和密钥进行异或运算,然后计算密文的长度,最后返回解密后的字符串。
  • 任务4:利用上面定义的三个函数,对下面两个字符串进行加解密操作。
    string1 = “路漫漫其修远兮,吾将上下而求索。”
    string2 = “Never put off until tomorrow what may be done today.”
  • 任务5:利用json 模块和pathlib包中的Path模块,分别定义一个加密文本文件的函数和一个解密文本文件的函数。
    提示:在实验过程中,用help()和dir()等帮助函数查阅相关模块、函数和方法的用法。

3.2 实验步骤:

按照二进制数异或的原理,对文本文件进行加解密。

  1. 加密操作
    首先将文本文件转换为二进制数,再生成与该二进制数等长的随机密钥,将二进制数与密钥进行异或操作,得到加密后的二进制数。
  2. 解密操作
    将加密后的二进制文件与密钥进行异或操作,得到原来的二进制数,再将二进制数恢复成文本文件。

4. 实验数据记录(或仿真及软件设计)

4.1 任务一:

4.1.1 代码:
import  secrets

def generateM(L):
    bys=secrets.token_bytes(L)  #返回包含nbytes个字节的字节字符串。
    # 转化成整数M
    # 只能用这个函数,用decode编码处理不了
    M=int.from_bytes(bys,byteorder='little',signed='true')
    return  M

 #print(generateM(10))
4.1.2 截图:

在这里插入图片描述

4.2 任务二:

代码:
def jiami(s):
    #字符串编码为字节串
    s=s.encode()
    length=len(s)
    #转换为整数
    zhengshu=int.from_bytes(s, byteorder='big',signed='true')
    #整数与密钥进行异或运算生成密文
    miyao=generateIntM(length)
    miwen=miyao^zhengshu
    return {'miyao': miyao,'miwen': miwen}

4.3 任务三:

代码:
def jiemi(miwen,miyao):
    afterJiemi=miwen^miyao
    #计算密文的长度,注意这里的+7/8
    length=int((afterJiemi.bit_length()+7)/8)
    #转化成字节流
    afterJiemi=int.to_bytes(afterJiemi,length,byteorder='big',signed='true')
    #解码成字符串
    afterJiemi=afterJiemi.decode()
    return  afterJiemi

4.4 任务四:

代码:
string1 = "路漫漫其修远兮,吾将上下而求索。"
string2 = "Never put off until tomorrow what may be done today."
#加密
JAM=jiami(string1)
print(JAM)
#解密
JEM=jiemi(JAM['miwen'],JAM['miyao'])
print(JEM)

#字符串2
JAM2=jiami(string2)
print(JAM2)
JEM2=jiemi(JAM2['miwen'],JAM2['miyao'])
print(JEM2)
以上四个任务运行截图:

在这里插入图片描述

4.5 任务五:

4.5.1 代码:
#加密文件
def jiamiText(path):
    path=Path(path) #此处为密钥路径
    jiamipath=input("请输入加密文件路径:")
    jiemipath=input("请输入加密后文件路径:")
    #如果你要处理的是文件而不是字符串,你可以使用 json.dump() 和 json.load() 来编码和解码JSON数据。
    with open(path,'wt',encoding='utf-8') as fp0 , \
            open(jiamipath,'rt',encoding='utf-8') as fp1 , \
            open(jiemipath,'wt',encoding='utf-8') as fp2 :
        #读取加密文件内容
        jiamitxt=jiami(fp1.read())

        #返回加密后的密文,密钥,并写入文件中
        miwen1,miyao1=jiamitxt['miwen'],jiamitxt['miyao']
        json.dump(miyao1,fp0)
        json.dump(miwen1,fp2)
        
#解密文件
def jiemiText():
    miyao_path=input("请输入密钥路径:")
    miwen_path=input("请输入待解密文件路径:")
    jiemi_path=input("请输入解密后文件路径:")
    with open(miwen_path,'rt',encoding='utf-8') as fp1 , \
            open(miyao_path,'rt',encoding='utf-8') as fp2,  \
            open(jiemi_path,'wt',encoding='utf-8') as fp3 :

        #解密操作
        jiemitxt=jiemi(json.load(fp2), json.load(fp1))
        fp3.write(jiemitxt)

path=input("要写入的密钥路径:")
jiamiText(path)
jiemiText()
4.5.2 截图:

在这里插入图片描述
在这里插入图片描述


五、实验结果分析及回答问题(或测试环境及测试结果)

本次实验有几个难点:

  1. 将字节流转化成数字,采用:int.from_bytes()函数,我尝试str()进行编码,发现不可行。
  2. 在解密过程中计算密文的长度,length=int((afterJiemi.bit_length()+7)/8)
    如果不采用+7将会出现溢出错误。
  3. 在于使用json于Path模块,之前没有使用过,正好通过这次了解学习查阅doc文档。
发布了29 篇原创文章 · 获赞 1 · 访问量 944

猜你喜欢

转载自blog.csdn.net/qq_40505187/article/details/104548357
今日推荐