我最近开始玩The Python Challenge。虽然相当复杂,但所需的编码并不十分困难,这使得学习许多有用的模块变得非常有趣。在
我的问题是关于17级的。我理解在收集曲奇的同时,按照4级所需的线索,我就是这样做的。但是,我不能对得到的字符串进行BZ2解压缩。在
我尝试了google,发现了一个很好的博客,里面有python2的解决方案。具体地说,17级的那个是here。通过分析,我意识到我确实得到了正确的压缩字符串(来自cookies),并且它在python2中得到了正确的解压:
bz2.decompress(urllib.unquote_plus(compressed))
但是,Python 3中的bz2.decompress
需要一个字节数组而不是一个字符串,但是明显的Python 3对应于上面的行:
失败,返回OSError: Invalid data stream
。我尝试了所有的standard encodings和上面的一些变体,但是没有用。在
到目前为止,我的(非工作)解决方案如下:
#!/usr/bin/env python3
"""
The Python Challenge #17: http://www.pythonchallenge.com/pc/return/romance.html
This is similar to #4 and it actually uses its solution. However, the key is in
the cookies. The page's cookie says: "you+should+have+followed+busynothing..."
So, we follow the chain from #4, using the word "busynothing" and
reading the cookies.
"""
import urllib.request, urllib.parse
import re
import bz2
nothing = "12345"
last_cookie = None
message = ""
while True:
headers = dict()
if last_cookie:
headers["Cookie"] = last_cookie
r = urllib.request.Request("http://www.pythonchallenge.com/pc/def/linkedlist.php?busynothing=" + nothing, headers=headers)
with urllib.request.urlopen(r) as u:
last_cookie = u.getheader("Set-Cookie")
m = re.match(r"info=(.*?);", last_cookie)
if m:
message += m.group(1)
text = u.read().decode("utf8")
print("{} >>> {}".format(nothing, text))
m = re.search(r"\d+$", text)
try:
nothing = str(int(m.group(0)))
except Exception as e:
print(e)
break
print("Cookies message:", message)
print("Decoded:", bz2.decompress(urllib.parse.unquote_plus(message).encode("utf8")))
所以,我的问题是:解决上述问题的Python3解决方案是什么样子的?为什么我的解决方案不能像预期的那样工作?在
我很清楚这其中的一部分可以做得更好。我想要一个快速而肮脏的解决方案,所以我在这里的兴趣只在于它能起作用(为什么不能像我上面所说的那样)。在
您需要在这里使用^{} function 。它不支持
+
到空间的映射,但这与str.replace()
无关:这样就可以很好地减压。您可以将生成的未压缩字符串解码为ASCII:
^{pr2}$演示使用一条不同的消息,我准备不泄露谜题:
另一种方法是用cd4-UTF代替cd4-UTF。
unquote_plus()
的默认错误处理程序设置为'replace'
,因此您不会注意到原始数据无法解码为UTF-8,因此字节被U+FFFD替换字符替换,这是导致解压缩失败的原因。Latin-1将oe上的所有字节1直接映射到前256个Unicode字符,因此您可以将其编码回原始字节:相关问题 更多 >
编程相关推荐