CIT 591 Programming suggestions
Fall 2009, David Matuszek

This repeats some of the things I said in class.

Functions should be short and single-purpose

For my Playfair program, I wrote 13 functions. The average length of a function, not counting comments, was 5.23 lines. The two longest functions (to encode a letter pair, and to decode a letter pair) were each 14 lines.

If you have a function that works and does something useful, don't add more code to it; write another function.

In the Playfair assignment, I gave you a seven-step algorithm for creating the code array. Most of those steps could be single functions.

Use Test-Driven Design

Seriously. It works.

As I said in lab, the two test functions that I provided, testEncode and testDecode, should be the last tests you try to get running. They are the top-level tests that you need to work toward.

You know you have to ignore whitespace, punctuation, digits, and everything but letters. Why not write a function that takes any string and returns a string containing only the letters from the given string? (Hint: If you import string, you have the function string.isalpha(). I wrote this on the board in lab.)

It's really easy to write a test for this function. Then you can write the function. Then you can go on to another function. You won't be tempted to "bury" the code for deleting non-alphabetic characters in some big function to create the code array.

One of the really nice things about TDD is that it lets you make steady, continuous progress. The next time you spend an hour trying to debug a 25-line function, think about this.

Here's a really short summary of TDD you should look at.

Avoid magic numbers

Some of you are using magic numbers like 97 in your program. Seriously, are you going to remember next week what this number is? If someone else looks at your program, will they know?

It's pretty much always okay to use the numbers 0 and 1. In my program I also use 5 and 25, without bothering to note that that's the size of the array and the number of elements in it--because this is the Playfair cipher, it uses a 5x5 array, always, and it's obvious in the code that I'm working with the array.

If you really need to change a character to a number (I didn't), do something like ord('a') instead of 97.

Programming hints

Communicate with your partner! Email, instant messaging, phone calls, whatever. Sitting together at one computer is best, but I realize you can't always do that. Come as close as you can.

Also, remember that the best way to learn is to teach.

The more you can rely on built-in methods, like lower() and isalpha(), the less code you have to write and debug. The Python Standard Library is your friend.

You can pass as many parameters as you like into a function, but a function can only return one value. Right? Right. But that value can be a tuple! For example,

def chopTwoCharacters(message):
    return (message[:2], message[2:])
This can be called as
(twoLetters, restOfMessage) = chopTwoCharacters(message)
or even as
twoLetters, restOfMessage = chopTwoCharacters(message)

I don't use this actual function in my program, but I use the idea. It's very useful!

Here's a Really Bad Idea: One partner writes the tests and the other partner writes the functions. I know this is a bad idea because some of my past students have tried it. Besides, it completely negates the value of TDD.

Do not make a last-minute change to your program--not even adding a comment!--just before you submit it. If you change even a single character, test it again before you submit it. This is always good advice, but this year, for the first time, you only get to submit once. If you mess it up, we have to discard your submission before you can submit again.