模拟转轮密码机
随便写的答辩代码不要太较真,题目在课本P54
第二版加了个类,第一版也还在下面
class Rotary:
def __init__(self):
self.count = 0
self.l1 = [24, 25, 26, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23]
self.l2 = [21, 3, 15, 1, 19, 10, 14, 26, 20, 8, 16, 7, 22, 4, 11, 5, 17, 9, 12, 23, 18, 2, 25, 6, 24, 13]
self.l3 = [26, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25]
self.l4 = [20, 1, 6, 4, 15, 3, 14, 12, 23, 5, 16, 2, 22, 19, 11, 18, 25, 24, 13, 7, 10, 8, 21, 9, 26, 17]
self.l5 = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26]
self.l6 = [8, 18, 26, 17, 20, 22, 10, 3, 13, 11, 4, 23, 5, 24, 9, 12, 25, 16, 19, 6, 15, 21, 2, 7, 1, 14]
def roll(self, l):
return [l[-1]] + l[:-1]
def encode(self, m):
if m >= 'A' and m <= 'Z':
m = ord(m) - 65
flag = 1
elif m >= 'a' and m<= 'z':
m = ord(m) - 97
flag = 0
else:
return m
m = self.l2.index(self.l1[m])
m = self.l4.index(self.l3[m])
m = self.l6.index(self.l5[m])
self.count += 1
self.l5 = self.roll(self.l5)
self.l6 = self.roll(self.l6)
if self.count % 26 == 0:
self.l3 = self.roll(self.l3)
self.l4 = self.roll(self.l4)
if self.count % (26**2) == 0:
self.l1 = self.roll(self.l1)
self.l2 = self.roll(self.l2)
if flag == 1:
m = chr(m + 65)
return m
else:
m = chr(m + 97)
return m
r = Rotary()
# 加密全文&字频统计
list = [0] * 26
f = open('message.txt', 'r', encoding = 'utf-8')
msg = f.read()
f.close()
cipher = ""
for i in msg:
c = r.encode(i)
cipher += c
if c >= 'a' and c <= 'z':
list[ord(c) - 97] += 1
elif c >= 'A' and c <= 'Z':
list[ord(c) - 65] += 1
f = open('cipher.txt', 'w', encoding = 'utf-8')
f.write(cipher)
print(cipher)
s = sum(list)
prob = [list[i]/s for i in range(26)]
for i in range(26):
print(f'{chr(i+97)} = {prob[i]}')
# 1.0
global l1, l2, l3, l4, l5, l6
global count
# 转轮初始状态
l1 = [24, 25, 26, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23]
l2 = [21, 3, 15, 1, 19, 10, 14, 26, 20, 8, 16, 7, 22, 4, 11, 5, 17, 9, 12, 23, 18, 2, 25, 6, 24, 13]
l3 = [26, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25]
l4 = [20, 1, 6, 4, 15, 3, 14, 12, 23, 5, 16, 2, 22, 19, 11, 18, 25, 24, 13, 7, 10, 8, 21, 9, 26, 17]
l5 = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26]
l6 = [8, 18, 26, 17, 20, 22, 10, 3, 13, 11, 4, 23, 5, 24, 9, 12, 25, 16, 19, 6, 15, 21, 2, 7, 1, 14]
# 转轮转动
def roll(l):
return [l[-1]] + l[:-1]
# 加密
def encode(m):
global count
global l1, l2, l3, l4, l5, l6
if m >= 'A' and m <= 'Z':
m = ord(m) - 65
flag = 1
elif m >= 'a' and m<= 'z':
m = ord(m) - 97
flag = 0
else:
return m
m = l1[m]
m = l2.index(m)
m = l3[m]
m = l4.index(m)
m = l5[m]
m = l6.index(m)
l5 = roll(l5)
l6 = roll(l6)
count += 1
if count % 26 == 0:
l3 = roll(l3)
l4 = roll(l4)
if count % (26**2) == 0:
l1 = roll(l1)
l2 = roll(l2)
if flag == 1:
m = chr(m + 65)
return m
else:
m = chr(m + 97)
return m
count = 0
list = [0] * 26
# 加密全文&字频统计
f = open('message.txt', 'r', encoding = 'utf-8')
msg = f.read()
f.close()
cipher = ""
for i in msg:
c = encode(i)
cipher += c
if c >= 'a' and c <= 'z':
list[ord(c) - 97] += 1
elif c >= 'A' and c <= 'Z':
list[ord(c) - 65] += 1
f = open('cipher.txt', 'w', encoding = 'utf-8')
f.write(cipher)
s = sum(list)
prob = [list[i]/s for i in range(26)]
for i in range(26):
print(f'{chr(i+97)} = {prob[i]}')