232

If you open a Python interpreter, and type "import this", as you know, it prints:

The Zen of Python, by Tim Peters

Beautiful is better than ugly.
Explicit is better than implicit.
Simple is better than complex.
Complex is better than complicated.
Flat is better than nested.
Sparse is better than dense.
Readability counts.
Special cases aren't special enough to break the rules.
Although practicality beats purity.
Errors should never pass silently.
Unless explicitly silenced.
In the face of ambiguity, refuse the temptation to guess.
There should be one-- and preferably only one --obvious way to do it.
Although that way may not be obvious at first unless you're Dutch.
Now is better than never.
Although never is often better than right now.
If the implementation is hard to explain, it's a bad idea.
If the implementation is easy to explain, it may be a good idea.
Namespaces are one honking great idea -- let's do more of those!

In the python source(Lib/this.py) this text is generated by a curious piece of code:

s = """Gur Mra bs Clguba, ol Gvz Crgref

Ornhgvshy vf orggre guna htyl.
Rkcyvpvg vf orggre guna vzcyvpvg.
Fvzcyr vf orggre guna pbzcyrk.
Pbzcyrk vf orggre guna pbzcyvpngrq.
Syng vf orggre guna arfgrq.
Fcnefr vf orggre guna qrafr.
Ernqnovyvgl pbhagf.
Fcrpvny pnfrf nera'g fcrpvny rabhtu gb oernx gur ehyrf.
Nygubhtu cenpgvpnyvgl orngf chevgl.
Reebef fubhyq arire cnff fvyragyl.
Hayrff rkcyvpvgyl fvyraprq.
Va gur snpr bs nzovthvgl, ershfr gur grzcgngvba gb thrff.
Gurer fubhyq or bar-- naq cersrenoyl bayl bar --boivbhf jnl gb qb vg.
Nygubhtu gung jnl znl abg or boivbhf ng svefg hayrff lbh'er Qhgpu.
Abj vf orggre guna arire.
Nygubhtu arire vf bsgra orggre guna *evtug* abj.
Vs gur vzcyrzragngvba vf uneq gb rkcynva, vg'f n onq vqrn.
Vs gur vzcyrzragngvba vf rnfl gb rkcynva, vg znl or n tbbq vqrn.
Anzrfcnprf ner bar ubaxvat terng vqrn -- yrg'f qb zber bs gubfr!"""

d = {}
for c in (65, 97):
    for i in range(26):
        d[chr(i+c)] = chr((i+13) % 26 + c)

print "".join([d.get(c, c) for c in s])
martineau
  • 119,623
  • 25
  • 170
  • 301
byterussian
  • 3,539
  • 6
  • 28
  • 36
  • 5
    Someone should rewrite this module so that it violates every single *one* of those principles :-) At the moment, it violates only a few. – paxdiablo Feb 21 '22 at 03:14

5 Answers5

213

This is called rot13 encoding:

d = {}
for c in (65, 97):
    for i in range(26):
        d[chr(i+c)] = chr((i+13) % 26 + c)

Builds the translation table, for both uppercase (this is what 65 is for) and lowercase (this is what 97 is for) chars.

print "".join([d.get(c, c) for c in s])

Prints the translated string.

Eli Bendersky
  • 263,248
  • 89
  • 350
  • 412
  • 28
    And that can actually be implemented more simply in both 2.x and 3.x as `import codecs; print(codecs.decode(s, "rot-13"))`. Writing the algorithm out by hand like that was just further obfuscation of the easter egg. – ncoghlan May 02 '11 at 12:21
  • 13
    Or just `'Gur Mra bs Clguba, ol Gvz Crgref'.decode('rot13')`. – Alex Brasetvik May 02 '11 at 19:24
  • 4
    Maybe we should add that ROT13 was the main "encryption" method used in the old usenet days 8^) – Zane May 21 '14 at 08:16
  • 57
    @OllieFord: As a joke. Everything the module does, from obfuscating the source code to implementing rot13 from scratch even though it's built into the stdlib, directly violates the Zen of Python. Tim Peters also snuck some subtle jokes into the Zen itself (notice the dashes on the TOOWTDI line do it two different ways?). – abarnert Sep 15 '14 at 21:09
  • 3
    I noticed that a lot of people use the word _encoding_, including the wiki. Isn't it _encryption_? It's not exactly encoded for some other process, it's obfuscation. – keyser Dec 20 '14 at 22:08
  • 1
    why does `this.c` evaluate to `!`? – Zach Mar 30 '15 at 20:34
  • @OllieFord *BURP* WHY NOT?! – TheBlackCat Jul 08 '15 at 12:01
  • 2
    @Zach because it is the last character of the zen of python considering we iterated over it with `for c in s` – Maxime R. Feb 02 '16 at 16:39
  • 10
    @abarnert I think the name of the module, `this`, is also part of the joke because other languages (e.g. Java) use `this` similar to how Python uses `self`. Typing `import this` looks just as pointless as typing `import java.self;`. – Luc Jun 16 '16 at 21:57
  • 2
    @keyser *Encryption* entails that only specific entities are able to *decrypt* a secret message; it requires a *secret key* as part of the process. An *encoding* has no secret, it's merely representing data in an *alternative* representation. If you know it's ROT13 encoded, you can easily decode it. If you know it's Base 64 encoded, or ASCII encoded, or percent-encoded, you can easily decode it. ROT13 is an *encoding*. – deceze Oct 17 '16 at 08:45
  • 3
    @deceze I hear what you're saying but I still see it as the encryption algorithm being rotation and the key being the length of the rotation. It's bad encryption, sure. Here's the start of the encryption wiki btw: "encryption is the process of encoding messages" :) – keyser Oct 21 '16 at 18:58
27

If you want to make the ROT13 substitution by hand - or in your head - you can check that because 13*2 = 26 (the number of the letters of the English alphabet), it's essentially an interchange:

a <-> n
b <-> o
c <-> p
...
m <-> z

A <-> N
B <-> O
C <-> P
...
M <-> Z 

Vs lbh cenpgvfr ybat rabhtu, lbh'yy riraghnyyl znfgre gur Mra bs EBG-13 nytbevguz naq ernq guvf Xyvatba ybbxvat grkgf jvgubhg pbzchgre uryc.

ypercubeᵀᴹ
  • 113,259
  • 19
  • 174
  • 235
18

It uses ROT13 encoding. This is used because it's a joke.

You can also use Python functions to decode string.

Python 2 only:

import this
print(this.s.decode('rot13'))

Python 2 & 3:

import codecs
print(codecs.decode(this.s, 'rot-13'))
Filip Š
  • 746
  • 2
  • 13
  • 22
trapwalker
  • 189
  • 1
  • 2
  • This was noticed by [ncoghlan comment on May 2 '11](https://stackoverflow.com/questions/5855758/what-is-the-source-code-of-the-this-module-doing/53591469#comment6730572_5855793) using `import codecs`. I do not know if importing codecs is still needed or if the availability of `decode` was made automatic with some particular release of Python. Could you link to the documentation of the `decode` that you're using? – Cœur Dec 03 '18 at 10:51
  • 1
    @Cœur This also does not work for me in Python 3.7 in IDLE. Maybe this was Python 2? – Filip Š Jan 03 '19 at 18:27
  • @FilipŠ oh, you're right, it works with Python 2 but not with Python 3. But in Python 2, you can just do `import this` and it will print it directly without any additional code. – Cœur Jan 04 '19 at 01:10
12

It's a substitution cipher, rot13.

Michael J. Barber
  • 24,518
  • 9
  • 68
  • 88
10

It's a substitution cipher (as mentioned in previous answers). Historically speaking, it's the Caesar cipher.

https://www.google.de/search?q=caesar+cipher&cad=h

bastelflp
  • 9,362
  • 7
  • 32
  • 67
  • I think Caesar cipher usually rotates the letters by three positions, not by [number of letters]/2 positions. – NerdOnTour Feb 02 '22 at 09:04