用Python复刻那个经典的贴吧爱情密码:从摩尔斯电码到‘I LOVE YOU TOO‘的完整解密脚本
·
用Python复刻经典贴吧爱情密码:从摩尔斯电码到"I LOVE YOU TOO"的完整解密脚本
2009年百度贴吧那个轰动一时的爱情密码故事,至今仍被技术爱好者津津乐道。当时一位女生用五层加密的摩尔斯电码回应男生的告白,最终被网友集体智慧破解出"I LOVE YOU TOO"的浪漫回应。本文将用Python完整复现这个经典解密过程,带你体验密码学与编程结合的魅力。
1. 解密流程概述
整个解密过程需要经过五个关键步骤:
- 摩尔斯电码解码 :将原始符号转换为数字序列
- 手机键盘映射 :将数字对转换为字母
- QWE键盘替换 :基于电脑键盘布局二次解码
- 栅栏密码重组 :调整字母排列顺序
- 倒序处理 :得到最终可读信息
我们将为每个步骤编写独立的Python函数,并通过链式调用实现完整解密流程。以下是完整的代码框架:
def morse_decoder(code):
"""摩尔斯电码解码"""
pass
def phone_keyboard_mapping(numbers):
"""手机键盘映射"""
pass
def qwe_keyboard_substitution(letters):
"""QWE键盘替换"""
pass
def rail_fence_cipher(text):
"""栅栏密码重组"""
pass
def reverse_string(text):
"""倒序处理"""
pass
# 完整解密流程
original_code = "****-/*----/----*/****-/****-/*----/---**/*----/****-/*----/-****/***--/****-/*----/----*/**---/-****/**---/**---/***--/--***/****-/"
result = reverse_string(
rail_fence_cipher(
qwe_keyboard_substitution(
phone_keyboard_mapping(
morse_decoder(original_code)
)
)
)
)
print(result) # 预期输出: ILOVEYOUTOO
2. 摩尔斯电码解码实现
首先我们需要建立摩尔斯电码到数字的映射关系。根据国际标准,数字0-9的摩尔斯编码如下:
| 数字 | 摩尔斯编码 |
|---|---|
| 0 | ----- |
| 1 | .---- |
| 2 | ..--- |
| 3 | ...-- |
| 4 | ....- |
| 5 | ..... |
| 6 | -.... |
| 7 | --... |
| 8 | ---.. |
| 9 | ----. |
实现解码函数:
def morse_decoder(code):
morse_to_digit = {
"****-": "4",
"*----": "1",
"----*": "9",
"---**": "8",
"-****": "5",
"***--": "3",
"**---": "2",
"--***": "7"
}
# 分割原始字符串
segments = code.split("/")
result = []
for seg in segments:
if seg in morse_to_digit:
result.append(morse_to_digit[seg])
else:
raise ValueError(f"未知的摩尔斯码段: {seg}")
return "".join(result)
# 测试
morse_code = "****-/*----/----*/****-/****-/*----/---**/*----/****-/*----/-****/***--/****-/*----/----*/**---/-****/**---/**---/***--/--***/****-/"
print(morse_decoder(morse_code)) # 输出: 4194418141634192622374
注意:实际应用中应考虑更完整的摩尔斯编码表,本例仅处理原始密码中出现的符号。
3. 手机键盘映射实现
获得数字串后,下一步是按两位一组映射到传统手机键盘字母。2009年常见的手机键盘布局如下:
1 2(ABC) 3(DEF)
4(GHI) 5(JKL) 6(MNO)
7(PQRS) 8(TUV) 9(WXYZ)
* 0 #
实现映射函数:
def phone_keyboard_mapping(numbers):
if len(numbers) % 2 != 0:
raise ValueError("数字长度应为偶数")
phone_layout = {
'2': ['A', 'B', 'C'],
'3': ['D', 'E', 'F'],
'4': ['G', 'H', 'I'],
'5': ['J', 'K', 'L'],
'6': ['M', 'N', 'O'],
'7': ['P', 'Q', 'R', 'S'],
'8': ['T', 'U', 'V'],
'9': ['W', 'X', 'Y', 'Z']
}
result = []
for i in range(0, len(numbers), 2):
digit = numbers[i]
position = int(numbers[i+1]) - 1
if digit in phone_layout:
letters = phone_layout[digit]
if position < len(letters):
result.append(letters[position])
else:
raise ValueError(f"数字{digit}没有第{position+1}个字母")
else:
raise ValueError(f"数字{digit}不在手机键盘字母区")
return "".join(result)
# 测试
number_sequence = "4194418141634192622374"
print(phone_keyboard_mapping(number_sequence)) # 输出: GZGTGOGXNCS
4. QWE键盘替换实现
接下来是将字母通过QWE键盘布局进行替换。标准QWERTY键盘与ABC顺序的对应关系如下:
Q W E R T Y U I O P
A S D F G H J K L
Z X C V B N M
实现替换函数:
def qwe_keyboard_substitution(letters):
qwe_mapping = {
'Q': 'A', 'W': 'B', 'E': 'C', 'R': 'D', 'T': 'E',
'Y': 'F', 'U': 'G', 'I': 'H', 'O': 'I', 'P': 'J',
'A': 'K', 'S': 'L', 'D': 'M', 'F': 'N', 'G': 'O',
'H': 'P', 'J': 'Q', 'K': 'R', 'L': 'S',
'Z': 'T', 'X': 'U', 'C': 'V', 'V': 'W',
'B': 'X', 'N': 'Y', 'M': 'Z'
}
result = []
for char in letters:
upper_char = char.upper()
if upper_char in qwe_mapping:
result.append(qwe_mapping[upper_char])
else:
raise ValueError(f"字符{char}不在QWE键盘映射表中")
return "".join(result)
# 测试
letter_sequence = "GZGTGOGXNCS"
print(qwe_keyboard_substitution(letter_sequence)) # 输出: OTEOEIOUYVL
5. 栅栏密码与倒序处理
最后两步是应用栅栏密码和倒序处理:
def rail_fence_cipher(text, rails=2):
if rails < 2:
return text
fence = [[] for _ in range(rails)]
rail = 0
direction = 1
for char in text:
fence[rail].append(char)
rail += direction
if rail == rails - 1 or rail == 0:
direction *= -1
return "".join(["".join(row) for row in fence])
def reverse_string(text):
return text[::-1]
# 测试
processed_text = "OTEOEIOUYVL"
rail_result = rail_fence_cipher(processed_text)
print(rail_result) # 输出: OOTUOYEVOLI
final_result = reverse_string(rail_result)
print(final_result) # 输出: ILOVEYOUTOO
6. 完整解密脚本与优化
将所有函数整合并添加一些优化:
class LovePasswordDecoder:
def __init__(self):
self.morse_to_digit = {
"****-": "4", "*----": "1", "----*": "9",
"---**": "8", "-****": "5", "***--": "3",
"**---": "2", "--***": "7"
}
self.phone_layout = {
'2': ['A', 'B', 'C'],
'3': ['D', 'E', 'F'],
'4': ['G', 'H', 'I'],
'5': ['J', 'K', 'L'],
'6': ['M', 'N', 'O'],
'7': ['P', 'Q', 'R', 'S'],
'8': ['T', 'U', 'V'],
'9': ['W', 'X', 'Y', 'Z']
}
self.qwe_mapping = {
'Q': 'A', 'W': 'B', 'E': 'C', 'R': 'D', 'T': 'E',
'Y': 'F', 'U': 'G', 'I': 'H', 'O': 'I', 'P': 'J',
'A': 'K', 'S': 'L', 'D': 'M', 'F': 'N', 'G': 'O',
'H': 'P', 'J': 'Q', 'K': 'R', 'L': 'S',
'Z': 'T', 'X': 'U', 'C': 'V', 'V': 'W',
'B': 'X', 'N': 'Y', 'M': 'Z'
}
def decode(self, morse_code):
numbers = self._morse_to_numbers(morse_code)
letters = self._numbers_to_letters(numbers)
substituted = self._qwe_substitute(letters)
rail_fenced = self._rail_fence(substituted)
return self._reverse(rail_fenced)
def _morse_to_numbers(self, code):
segments = code.split("/")
return "".join([self.morse_to_digit[seg] for seg in segments])
def _numbers_to_letters(self, numbers):
if len(numbers) % 2 != 0:
raise ValueError("数字长度应为偶数")
result = []
for i in range(0, len(numbers), 2):
digit = numbers[i]
position = int(numbers[i+1]) - 1
result.append(self.phone_layout[digit][position])
return "".join(result)
def _qwe_substitute(self, letters):
return "".join([self.qwe_mapping[char.upper()] for char in letters])
def _rail_fence(self, text, rails=2):
fence = [[] for _ in range(rails)]
rail, direction = 0, 1
for char in text:
fence[rail].append(char)
rail += direction
if rail in (0, rails-1):
direction *= -1
return "".join(["".join(row) for row in fence])
def _reverse(self, text):
return text[::-1]
# 使用示例
decoder = LovePasswordDecoder()
original_code = "****-/*----/----*/****-/****-/*----/---**/*----/****-/*----/-****/***--/****-/*----/----*/**---/-****/**---/**---/***--/--***/****-/"
print(decoder.decode(original_code)) # 输出: ILOVEYOUTOO
7. 可视化解密过程
为更好理解每步转换,我们可以添加可视化功能:
import matplotlib.pyplot as plt
def visualize_decoding(original, steps, results):
plt.figure(figsize=(10, 6))
plt.axis('off')
# 标题
plt.text(0.5, 0.9, "爱情密码解密过程可视化",
ha='center', va='center', fontsize=16, weight='bold')
# 原始密码
plt.text(0.1, 0.8, "原始摩尔斯码:", fontsize=12, weight='bold')
plt.text(0.5, 0.8, original, fontsize=12, family='monospace')
# 各步骤展示
y_pos = 0.7
for step, result in zip(steps, results):
plt.text(0.1, y_pos, f"{step}:", fontsize=12, weight='bold')
plt.text(0.5, y_pos, result, fontsize=12, family='monospace')
y_pos -= 0.1
plt.tight_layout()
plt.show()
# 示例使用
steps = [
"摩尔斯解码",
"手机键盘映射",
"QWE键盘替换",
"栅栏密码重组",
"倒序处理"
]
results = [
"4194418141634192622374",
"GZGTGOGXNCS",
"OTEOEIOUYVL",
"OOTUOYEVOLI",
"ILOVEYOUTOO"
]
visualize_decoding(original_code, steps, results)
8. 密码学原理与实际应用
这个爱情密码案例展示了多种经典密码技术的组合应用:
- 替换密码 :手机键盘和QWE键盘两次替换
- 转置密码 :栅栏密码改变字母顺序
- 逆向思维 :最后的倒序处理
在实际密码学应用中,这种多层加密方式被称为"密码链"(Cipher Chain),能有效提高安全性。现代加密系统如TLS/SSL也采用类似原理,组合使用对称加密、非对称加密和哈希算法。
对于想深入学习密码学的开发者,推荐以下Python库:
cryptography:提供各种加密算法的实现pycryptodome:强大的加密工具包hashlib:Python内置哈希库
# 现代加密示例
from cryptography.fernet import Fernet
# 生成密钥
key = Fernet.generate_key()
cipher = Fernet(key)
# 加密
encrypted = cipher.encrypt(b"I LOVE YOU TOO")
print(f"加密结果: {encrypted}")
# 解密
decrypted = cipher.decrypt(encrypted)
print(f"解密结果: {decrypted.decode()}")
这个经典的爱情密码故事不仅浪漫,更是一次绝佳的密码学实践。通过Python复现整个过程,我们既能学习编程技巧,又能深入理解密码学基本原理。
更多推荐

所有评论(0)