Python Challenge通关攻略及代码(第0至5关)

Python Challenge是一个好玩的闯关网站,也是初学者用于练手的好材料。已经收藏了该网站很久,但一直没有开始尝试,近日心血来潮,本文记录了第0至5关的通关攻略及代码。

第0关:warming up

原始url为:http://www.pythonchallenge.com/pc/def/0.html
第0关界面

0.1 攻略

界面上是2的38次幂,使用Python计算结果,替换url后缀,修改url为http://www.pythonchallenge.com/pc/def/274877906944.html

0.2 代码

print(2 ** 38)

""" 
Output: 274877906944
"""

第1关:What about making trans?

url:http://www.pythonchallenge.com/pc/def/274877906944.html
第1关界面

1.1 攻略

界面上字母K向后移2位变成字母M,字母O向后移2位变成字母Q,字母E向后移2位变成字母G,因此考察移位密码,将url后缀向后移2位并替换,修改url为http://www.pythonchallenge.com/pc/def/ocr.html

1.2 代码

def decrypt(s):
    res = ""
    for c in s:
        if c not in [" ", ".", "(", ")", "'"]:
            res += chr(ord('a') + (ord(c) + 2 - ord('a')) % 26)
        else:
            res += c
    return res
# 解密提示
print(decrypt("g fmnc wms bgblr rpylqjyrc gr zw fylb. rfyrq ufyr amknsrcpq ypc dmp. bmgle gr gl zw fylb gq glcddgagclr ylb rfyr'q ufw rfgq rcvr gq qm jmle. sqgle qrpgle.kyicrpylq() gq pcamkkclbcb. lmu ynnjw ml rfc spj."))
# Output: 
# i hope you didnt translate it by hand. thats what computers are for. doing it in by hand is inefficient and that's why this text is so long. using string.maketrans() is recommended. now apply on the url.

# 解密答案
print(decrypt("map"))

"""
Output: ocr
"""

第2关:ocr

url:http://www.pythonchallenge.com/pc/def/ocr.html
第2关界面

2.1 攻略

根据界面提示查看源代码,在源代码注释中发现谜题,找出出现次数最少的字符为:a, l, q, i, y, u, t, e,组成单词为equality,因此修改url为http://www.pythonchallenge.com/pc/def/equality.html
第2关源代码中隐藏的谜题

2.2 代码

from collections import Counter

def getRareChar(s):
    cnt = Counter(s)
    sorted_cnt = sorted(cnt.items(), key=lambda x:x[1])
    return sorted_cnt
# 字符串过长,用文件存储
with open('2-input.txt') as f:
    s = f.read()
print(getRareChar(s))

"""
Output:
[('a', 1),
 ('l', 1),
 ('q', 1),
 ('i', 1),
 ('y', 1),
 ('u', 1),
 ('t', 1),
 ('e', 1),
 ('\n', 1219),
 ('^', 6030),
 ('*', 6034),
 ('&', 6043),
 ('$', 6046),
 ('{', 6046),
 ('+', 6066),
 ('!', 6079),
 ('%', 6104),
 ('}', 6105),
 ('[', 6108),
 ('_', 6112),
 ('#', 6115),
 (']', 6152),
 ('(', 6154),
 ('@', 6157),
 (')', 6186)]
"""

第3关:re

url:http://www.pythonchallenge.com/pc/def/equality.html
第3关界面

3.1 攻略

与上一关相同,字符串数据隐藏在源代码中,使用正则表达式匹配“1个小写字母两边各有3个大写字母”的模式,
最终得到linkedlist,因此修改url为http://www.pythonchallenge.com/pc/def/linkedlist.html,进一步提示跳转至http://www.pythonchallenge.com/pc/def/linkedlist.php
第3关源代码中隐藏的字符串

3.2 代码

import re

with open('3-input.txt') as f:
    s = f.read()

iteritems = re.finditer(r'[^A-Z][A-Z]{3}([a-z])[A-Z]{3}[^A-Z]', s, re.M)

res = []
for m in iteritems:
    res.append(m.group(1))
print(''.join(res))

"""
Output: linkedlist
"""

第4关:follow the chain

url:http://www.pythonchallenge.com/pc/def/linkedlist.php
第4关界面

4.1 攻略

  1. 界面上没有明显提示,因此继续前几关的思路,查看源代码,发现隐藏提示"urllib may help. DON’T TRY ALL NOTHINGS, since it will never end. 400 times is more than enough."
  2. 发现图片链接地址为http://www.pythonchallenge.com/pc/def/linkedlist.php?nothing=12345
    第4关源代码中隐藏的提示
  3. 点击图片跳转至http://www.pythonchallenge.com/pc/def/linkedlist.php?nothing=12345,界面显示“and the next nothing is 44827”,因此需要通过界面内容不断修改“nothing=”后缀,使用urlib模拟网页请求循环400次(循环,即应了题目follow the chain的含义),循环中得到“peak.html”,最终答案为http://www.pythonchallenge.com/pc/def/peak.html

4.2 代码

from urllib.request import urlopen

response = urlopen("http://www.pythonchallenge.com/pc/def/linkedlist.php?nothing=12345")
for i in range(400):
    suffix = response.read().decode('utf-8').split()[-1]
    if suffix.find('.html') != -1:
        print(suffix)
        break
    url = "http://www.pythonchallenge.com/pc/def/linkedlist.php?nothing=" + suffix
    response = urlopen(url)

"""
Output: peak.html
"""

第5关:peak hell

url:http://www.pythonchallenge.com/pc/def/peak.html
第5关界面

5.1 攻略

  1. 界面上提示“pronounce it”,查看源代码发现提示“peak hell sounds familiar ?”
    第5关源代码中隐藏的提示

  2. 继续阅读源代码,发现奇怪的源文件“banner.p”,点击在新标签页打开发现隐藏数据
    奇怪的banner.p
    banner.p中的数据

  3. 这时结合上面的发现,“peak hell”读音类似“pickle”,使用pickle反序列化banner.p,得到“channel”,因此最终修改url为http://www.pythonchallenge.com/pc/def/channel.html进入第6关。

5.2 代码

import pickle

with open('banner.p', 'rb') as f:
    s = f.read()
    data = pickle.loads(s)
for item in data:
    for ch, cnt in item:
        print(cnt * ch, end="")
    print()

输出:
第5关代码输出结果

猜你喜欢

转载自blog.csdn.net/baidu_40395808/article/details/130966859