A first look at Python
Around a year ago I read the O’Reilly ‘Learning Python’ book and since then I’ve been looking for a quick, interesting and easy challenge to put it to use.
Around two years ago a friend bought me a copy of “The Code Book – the secret history of codes and code-breaking” by Simon Singh. At the time I thought “cheers, that looks dull”, but as usual I was completely wrong. It’s probably one of the most interesting books I’ve ever read. Even better than Alex James autobiography and everyone knows I love that since for about 3 months all I talked about was carrots and 120bpm.
Anyway, The Code Book introduced me to the Vigenere Cipher, a method that uses a key phrase to encrypt any plain text. This encryption method seemed like a great opportunity to put together a little code that takes a key phrase and some plain text and encrypts one with the other.
Heres my attempt.
The unit test:
1 import unittest; 2 from CypherMachine import *; 3 4 class CypherMachineTest(unittest.TestCase): 5 6 def test_encrypt(self): 7 test_string = 'thisisateststring'; 8 expected_result = 'clabmkjxwbxkcvawk'; 9 10 machine = CypherMachine(); 11 encrypted_string = machine.encrypt('jes',test_string); 12 13 assert encrypted_string == expected_result 14 15 16 if __name__ == "__main__": 17 unittest.main();
The implementation:
1 class CypherMachine: 2 def encrypt(self,key,plain_text): 3 encrypted_text = '' 4 5 position = 0 6 while position < len(plain_text): 7 for key_letter in key: 8 if position == len(plain_text): 9 break 10 encrypted_text = encrypted_text + self.encryptLetter(key_letter,plain_text[position]) 11 position = position + 1 12 13 return encrypted_text 14 15 def encryptLetter(self,key_letter,plain_letter): 16 17 key_position = ord(key_letter) 18 plain_letter_position = ord(plain_letter) 19 20 #96 being the number to bring lower case letters to there position in the alphabet 21 #-1 since the cyper square starts with b 22 key_alphabet_position = ord(key_letter) - 96 - 1 23 24 encrypted_position = plain_letter_position + key_alphabet_position 25 26 if encrypted_position > ord('z'): 27 encrypted_position = encrypted_position - 26 28 29 encrypted_letter = chr(encrypted_position) 30 return encrypted_letter
I know it’s not as neat or as simple as it should be but for an hours work I’m pretty happy with it. I love that fact that in Python you don’t waste time typing inconsequential characters like ‘{’ and ‘;’. I also like the fact that the parser makes you indent your code properly. But the best thing about Python is how easy it was to test. If I’d written this class in PHP I would have had to downloaded Simpletest or PHPUnit, read a little about how they work (to be fair, they’re both easy to use), find and included the files I wanted, then get on with the job of coding. With Python it’s just so easy. Import the unittest modules and get on with it. Perfect!
Maybe if testing in PHP was this easy I’d get fewer dirty looks when I tell people I’m a PHP developer.
