A Better Example of Maintainability

December 22, 2008 by diondock

There’s a school of thought for programming that says you don’t ship until you have everything in order. I mean, you don’t want to look like an idiot, right? There’s another school of thought that says you bang out release 1.0 as fast as possible, get feedback and iterate. Yesterday, I decided to just bang out a blog while it was fresh in my mind. The result? Mistakes, but instant feedback from people who care!

I was trying to give an example of how variable names can seem appropriate at the time but fail for the long haul.

There was some original code that looks similar to the following. It’s not the exactly the following, as I have no control over the copyright; perhaps that wasn’t obvious. Since it’s already written, complaining that it wasn’t done correctly The First Time makes me feel warm and fuzzy, but doesn’t help.

if (4 == some_function()) {
    /* talking to old process */
}
...
if (4 == some_function()) {
    /* talking to old process */

Not too good. A comment is needed to explain what’s going on. Plus we have that mysterious check all over the place.


#define OLD_PROC_VAL 4
...
old_process = (OLD_PROC_VAL == some_function());
...
if (old_process) {
    /* talking to old process */

That’s better. The check is done once and it should be clear the code is talking to the old process. But what will this mean four years from now when every process is old and another flavor of process is introduced? We now have old #1 and old #2? Someone is going to have to dig through the revision control logs to see which process was in use when the original old process check was added.

Oh, and just for fun, let’s say that some_function returns a value that has nothing to do with the version number of the old process.

I propose the version should go into the variable’s name:


#define PRE_RELEASE_15_MAGIC 4
...
pre_release_15 = (PRE_RELEASE_15_MAGIC == some_function());
...
if (pre_release_15) {
    /* Talking to process older than release 15 */

Now you can argue whether the final comment is necessary.

So what’s the point? Even the best architecture is still has to be implemented. You’re going to get old code and the only way to understand it is by reading. Make it easy for the others. Leave some breadcrumbs for them to follow.

An Example of Maintainability

December 20, 2008 by diondock

Original code:

if (x < 15) {
    /* talking to old parent */

then

old_parent = (x < 15);
if (old_parent) {
    /* talking to old parent */

finally

pre_release_15 = (x < 15);
if (pre_relelease_15) {
    /* Talking to parent older than release 15 */

although you could argue whether the final comment is even necessary.

Tabbed Code in WordPress

December 18, 2008 by diondock

It’s been driving me nuts that code doesn’t get tabbed in WordPress. The WordPress editor won’t allow tabs, but pasted in code usually has them. The solution is to use <pre> tags around the code tags. Here is the difference:

without <pre>

if (foo < bar) {
bar++;
}

with <pre>

if (foo < bar) {
    bar++;
}

and here’s just <pre> without <code>

if (foo < bar) {
    bar++;
}

which should make you wonder what’s the point of their code tags.

Sign of Quality

December 18, 2008 by diondock

I spent many years testing software. At the time, I considered quality software to be free of bugs.

For the last few years, I’ve been doing development. And I’m considering another aspect of software quality: the ability to have bugs fixed quickly. I’m not lobbying for delivering code without some degree of confidence it works but whether 99% confidence should be a goal.

For one thing, it actually sucks to test something and not find problems–assuming it’s not the final version. So the presence of a few bugs actually is motivating for testing. Plus, if your testers aren’t finding bugs, it seems like they would get sloppy over time, since they aren’t expecting anything. For example, how often do you check your car’s tires to see if they’re flat? How often do you check after getting a flat?

What are some good things about fixing bugs quickly?

  • It demonstrates you care about quality. The tester is happy because they’re vindicated (e.g. they aren’t told it isn’t important or there isn’t time).
  • It demonstrates your code is easy to modify.
  • It demonstrates your development processes are efficient.

So go and write some bugs today. Just be sure you can fix them ASAP.

practice

December 8, 2008 by diondock

Steve Yegge, when talking about interviewing, has asked candidates to write a program in their favorite language…and their second favorite. What a great idea!

Turns out it’s easy to get tripped up by syntax. Maybe this wouldn’t happen if I was switching languages more often.

Here’s the infamous FizzBuzz:

Python
too many blank lines:

def fizzBuzz2():
    for i in range(1, 101):
        print i,
        if i % 3 == 0:
            print("Fizz"),
        if i % 5 == 0:
            print("Buzz"),
        print "\n"

better formatting

def fizzBuzz3():
    for i in range(1, 101):
        msg = str(i) + " "
        if i % 3 == 0:
            msg += "Fizz"
        if i % 5 == 0:
            msg += "Buzz"
        print msg

Perl

for $i (1..100) {
        print $i;
        print "Fizz" if $i % 3 == 0;
        print "Buzz" if $i % 5 == 0;
        print "\n";
}

Java

class FizzBuzz {
    public static void main(String args[]) {
        for (int i = 1; i <= 100; i++) {
            System.out.print(i + " ");
            if (i % 3 == 0) {
                System.out.print("Fizz");
            }
            if (i % 5 == 0) {
                System.out.print("Buzz");
            }
            System.out.print("\n");
        }
    }
}

C

#include 

int main()
{
    int i;

    for (i = 1; i <= 100; i++) {
        printf("%d", i);
        if (i % 3 == 0) {
            printf("Fizz");
        }
        if (i % 5 == 0) {
            printf("Buzz");
        }
        printf("\n");
    }
    return 0;
}

Curious Reasoning

December 5, 2008 by diondock

“Uncle Bob” at Object Mentor took a moment to remind us that we should be responsible for our efforts, instead of blaming the framework. http://blog.objectmentor.com/articles/2008/11/16/dirty-rotten-scrumdrels.

Which prompted me to ask:
If scrum cannot be blamed for failure, can it take credit for success?

No one wanted to touch that question.

If you’re an agilist, you’d have to say No. Per the Agile manifesto, the people make the difference, and the methodology is less valued.

This leads to curious reasoning: When people are valued more than process (e.g. an agile framework), [agile] methodologies aren’t responsible for success. Conversely, when process is valued more, then the methodology is responsible for the outcome.

No wonder agile is a popular buzzword. If you declare yourself to be agile, then failure is not the fault of agile. And success is usually credited to suddenly being agile, whether it is responsible or not. Heads I win, tails you lose.

Worst Phrase Ever

November 4, 2008 by diondock

Steve Yegge has a great hint about Avoiding Weasel Words.

Here’s a personal favorite: help coordinate. You’re not doing, you’re not coordinating, you’re helping. Even that’s iffy; usually people have to ask for help.

malloc hint

September 5, 2008 by diondock

The rest of the world already knew this, but here’s a quick way to make malloc more flexible. My old code would read something like

SOMETHING *foo = NULL;
...
foo = malloc(sizeof(SOMETHING));

Which is great, except I need to know the exact name of foo’s data type and will have to change this reference it changes. Instead, use

SOMETHING *foo = NULL;
...
foo = malloc(sizeof *foo);

Buying a Laptop

August 2, 2008 by diondock

We needed to get a laptop for college. This should have been easy for technical professionals, right? If only.

We initially looked at Lenovos, since my wife works at IBM. They were well rated in Consumer Reports, err, a leading consumer magazine. Unfortunately, we’d been told that someone’s college machine got caught up in customs for 8 weeks and their “deal of the month” was coming due. We passed.

Then I was leading towards a MacBook. The 13″ model with extended warranty (I’m not taking bets that this laptop will stay only in the dorm room) ends up around $1500…but the student gets a free iPod, maybe in case they’re from Mars and don’t have one. Too much money.

My company gets all of our machines from Dell. They would give me the best discount on our “corporate” configurations. $1150 with a three year warranty, and the hardware seems decent. Still, we’re trying to go below $1000.

Then I stopped by Costco. They have a HP dv2931cl for $900 with a $100 off coupon. 250 Gbyte disc, 4 Gbyte RAM, wireless A/G/N and Vista 64 (so it can actually use that fourth gig). I’m a little nervous about driver support for Win64, but it looks like our iPod, camera and tablet all have drivers. So that’s our choice.

Then, this weekend, I read Consumer Reports rating of HP support as middling. Ah, well, let’s hope for the best.

No Such Thing as Negative Productivity

May 10, 2008 by diondock

Many people who blog about software talk about good programmers and bad ones. There’s a certain school of thought that says the worst programmers end up being a net negative to productivity. When I first heard that idea, it seemed odd. If that were really the case, how does a typical team (assuming half are below the industry average and half above) get anything done? I’d like to explore why that idea is close but not quite right.

Let’s ignore the case of psychotic behavior and focus on programming ability instead of mental state. I won’t argue that a troubled individual can destroy a team.

I submit the worst programmer gets literally nothing done. What do I mean? They won’t be competent enough to do any damage, because that would mean they’d have to figure out revision control or an IDE. It’s just not going to happen for them. They won’t write specs or docs because that would be evidence of their ignorance. They’ll be a ghost within a year, since they will leave no trace

  • no checkins
  • no defects filed
  • no defects fixed
  • no docs written
  • no specs written

Let’s go a step up from there. Now we have someone who is productive but sloppy. They understand things well enough to make changes but the quality is inferior. What does that mean? More rework! Someone will have to go back and clean up what they’ve done, either fixing bugs or getting things finished. At the end of the day they will have something to show but they won’t be able to fix it without help. This is probably the norm for most people and companies: slow, steady and non-optimal.

Now this rework could be thought of as negative progress. But it seems impossible to add so much negative progress that the project is better off sending the contributor to sit in meetings. If the progress were negative, it seems that in short time everything would be broken, right down to the hardware.

There are many famous software project failures, but we just don’t hear about failures due to complete breakage: nothing could be built, all source lost, and so on.

Instead, what we see is effectively a tax on the coworkers. They do their work plus a chunk of rework time to get the other things fixed. It’s just not negative productivity though, because something is still being produced at the end of the day.