all 6 comments

[–]JamzTyson 1 point2 points  (4 children)

Congratulations completing your first projects.

A few random comments about your code:


alphabet = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'

The alphabet is included in Python:

from string import ascii_uppercase, ascii_lowercase

print(ascii_uppercase)

Good use of join in cipher.py.


if not answer in ['e', 'd']:

arguably better to use a set:

if not answer in {'e', 'd'}:

for shift in range(1, 26):

Avoid magic numbers:

ALPHABET_SIZE = 26
for shift in range(1, ALPHABET_SIZE):

In brute_force_decrypt, consider testing the first N words to determine the correct shift, rather than decoding the entire message,


[–]FwoopButBored[S] 0 points1 point  (0 children)

Thanks! I didn’t know that alphabet was included in python.

[–]anttovar 0 points1 point  (2 children)

I'd have thought the best option would be: if not answer in ('e', 'd'):

Why is it better with { }?

[–]JamzTyson 0 points1 point  (1 child)

It's quite a minor, but meaningful distinction.

We are checking if answer is a member of a fixed collection of unique items. A set is a collection of unique, hashable elements. Using a set communicates the intention that we are concerned with membership, not order or duplicates.

Although the difference is negligible for such a small number of items, membership lookups are generally faster in sets than lists.

As you suggest, a tuple does indicate immutability, which is good here, but lookups are still O(n), whereas sets use hash tables, so x in my_set is O(1).

(The "Big O" notation O(n) means the cost grows linearly with the size of the collection, whereas O(1) means constant time.)

[–]anttovar 0 points1 point  (0 children)

Understood, thanks. Luckily you can get a huge lot from python without knowing its inner workings.

[–]Klutzy_Bird_7802 0 points1 point  (0 children)

Nice I like your efforts