programming

How to Learn Programming, in Two Easy Steps

I am sometimes asked by non-programmers how they can get into programming. They want to know what programming language they should learn, which programming tools to use, and so on. These are hard questions to answer. It's like asking "I'd like to be a musician. Which instruments and which pieces of music should I learn?"

Here is my advice:

  1. Think about an application you'd like to see developed.
  2. Learn what you need to know to develop that app, and develop it.

Programming is a big field. Choosing a concrete goal narrows it to something manageable. Once you know exactly what you want to make, it is a lot easier to decide upon a programming language and tools.

Professional programmers don't "learn how to program" and then just apply that knowledge for the rest of their careers. Every day, we learn new things: programming languages, tools, libraries, operating systems, and so on. We pick it up as we go, learning what we need to know as it's needed. If you want to be a programmer, you need to learn how to do the same.

Know Your Programming Languages

I am often amazed at how little some of my colleagues know or care about their craft. Something that constantly frustrates me is that people don't want to learn any more than they need to about the programming languages they use every day. Many programmers seem content to learn some pidgin sub-dialect, and stick with that. If they see a keyword or construct that they aren't familiar with, they'll complain that the code is "tricky."

What would you think of a civil engineer who shied away from calculus because it had "all those weird math symbols?"

I'm not suggesting that we all need to become "language lawyers." But if you make your living as a programmer, and claim to be a competent user of language X, then I think at a minimum you should know the following:

  • What are all the keywords of the language?
  • What are all the valid syntactic forms?
  • How are memory, files, and other operating system resources managed?
  • Where is the official language specification and library reference for the language?

The last one is the one that really gets me. Many programmers seem to have no idea that there is a "specification" or "standard" for any particular language. I still talk to people who think that Microsoft invented C++, and that if a program doesn't compile under VC6, it's not a valid C++ program.

Programmers these days have it easy when it comes to obtaining specs. Newer languages like C#, Java, Python, Ruby, etc. all have their documentation available for free from the vendors' web sites. Older languages and platforms often have standards controlled by standards bodies that demand payment for specs, but even that shouldn't be a deterrent: the C++ standard is available from ISO for $30 (and why am I the only person I know who has a copy?).

Programming is hard enough even when you do know the language. If you don't, I don't see how you have a chance.

Booleans Shouldn't Be Complicated

Warning: Geeky programmer content below.

While learning a new codebase, I was a little disturbed when I saw this:

  enum IsVerifying {
    IsVerifyingFalse,
    IsVerifyingTrue
  };

  enum IsVerified {
    IsVerifiedFalse,
    IsVerifiedTrue
  };

  enum IsEnabled {
    IsEnabledFalse,
    IsEnabledTrue
  };

  enum IsActive {
    IsActiveFalse,
    IsActiveTrue
  };

  enum IsOnline {
    IsOnlineFalse,
    IsOnlineTrue
  };

  /* etc. (There are about a dozen more of these.) */

And there was a lot of verbose code for dealing with these types, such as

  if (Verified()) {
    verified = IsVerifiedTrue;
  }
  else {
    verified = IsVerifiedFalse;
  }

  if (Enabled()) {
    enabled = IsEnabledTrue;
  }
  else {
    enabled = IsEnabledFalse;
  }

  /* etc. */

What's wrong with using plain-old-Boolean values false and true, or 0 and 1?

Well, after poking around the code more, I did find the reason that the original programmer did this. He has a lot of functions that take several flags as parameters, and something like this:

  SetStates(IsVerifyingFalse,
            IsVerifiedTrue,
            IsEnabledTrue,
            IsActiveFalse,
            IsOnlineFalse);

is easier to understand than something like this:

  SetStates(false, true, true, false, false);

But still, yyeeaagghh is the proper reaction to seeing something like this.

Proud Teacher

Today, a development team I've worked with solved an architectural problem by adding a factory method. And they did it without any prompting from me!

They grow up so fast.

Good-bye SCons, Hello CMake

Last year, I wrote of my initial impressions of SCons for controlling software builds. My initial impressions were positive, but even then I was wary of performance issues.

A few months later, I wrote about a performance problem with SCons and MSVC. I was able to hack SCons to make things a little better.

Things weren't bad for me, because I've been doing all my development on Linux, where SCons is pretty well-behaved. But the Windows developers hated it. SCons will build MSVC project files so that developers can edit and browse code through the IDE, but the builds are still controlled by SCons, and SCons was painfully slow on Windows. As the codebase grew, SCons got slower and slower.

The boss put up with it for a while, but he finally decided that enough was enough. I was ordered to find something better than SCons for our cross-platform builds.

We weren't the only people dissatisfied with SCons. The KDE team had tried SCons, found it lacking, then started their own Python-based build system based on SCons, which eventually became Waf. I looked at Waf briefly, but the immaturity of the project and lack of documentation turned me off.

I read that the autotools system was starting to provide better support for Windows, but I didn't think that solution would go over well with the team members and leaders who passionately hate things that are too UNIX-ish.

So, after reading that the KDE team finally settled on CMake, I decided to give that a try.

I've spent the last couple of days translating build scripts from SCons into CMake. So far, I'm pretty pleased with the results.

Pros of CMake over SCons:

  • It generates real honest-to-goodness MSVC solution and project files that work as well as or better than those that Windows developers would create by hand. The CMake developers don't treat Windows developers as second-class citizens.
  • The default compiler settings in the generated MSVC files and Makefiles are remarkably sane.
  • It has lots of functionality built in. (In contrast, SCons often required lots of code to be written to do simple things.)
  • It provides a simple mechanism for handling unit tests.
  • Simpler support for hierarchical builds.
  • It has the feel of something that has been used for real-world work. (In contrast, SCons always felt like a grad student's summer project.)
  • I don't have to go take a coffee break every time I need to do a build.

Cons:

  • I don't like CMake's syntax. It's like they took the syntaxes of Make, Perl, Bourne shell, and BASIC, and mixed them all together. (Please, people, stop inventing your own application-specific scripting languages! Especially if you are going to invent one that sucks.)
  • Online documentation is poor. You have to buy a $50 book if you want to figure things out in a reasonable amount of time.
  • While it is cross-platform, you still have to write a lot of "IF( WINDOWS ) ... ELSE ..." code.
  • It has no built-in support for precompiled headers. (But then again, neither did SCons. As with SCons, you can use precompiled headers by writing some code.).

I'm happy with the switch to CMake, and I'm sure the boss will be too. But who knows; maybe next year I'll be writing yet another blog entry about the need to adopt a new build system.

Death March

The term "death march" is commonly used for software projects that are behind schedule, over budget, have no end in sight, and yet must be completed. There is a book with that title.

I've recently become involved in one of these projects. I should say "re-involved," because I was involved with the project a year and a half ago, and I quit. As an independent contractor now, I feel less pain than the employees do: I get paid by the hour and can set my own schedule, whereas they have to work unpaid overtime, and they are shackled to their desks.

Yesterday, one of the developers had to go to a doctor. The stress and long hours had led to high pulse rate and other signs of anxiety. The doctor told him to go home and get some rest, which he did.

We're all glad that nothing more serious happened. Managers express surprise that anyone would work himself so hard. I've only been involved with this for a few days, but here's what I've observed:

  • Requirements and UI design are still changing.
  • Work that was originally estimated to take three months has now been scheduled for completion in three weeks.
  • A manager stops by every hour to get a status update.
  • There are a couple of hour-long meetings every day. Plans are changed during each meeting.

Yeah, I can't imagine why anyone would feel pressure, with management being so "helpful."

He's young. I remember when I was younger. I tried to meet crazy deadlines. I took it personally when managers demanded faster progress. I blamed myself for everything that went wrong. I worked myself sick.

Now, with a couple of decades of seasoning, I know better. If you're involved in a death march, it is due to your managers' incompetence, not yours. Work at a sustainable pace, and remember that no matter how loudly the managers are screaming, there is no need to sacrifice yourself for the good of the company.

No

Kris, the production system isn't working since we installed the newest release. Can you tell us how to fix it?

Can you send me the log files?

No. They are too big.

Will you let me access the system myself to see what's going wrong?

No. Developers can't touch the production system.

OK, can I access the test system to see if it exhibits the same behavior as the production system?

No. The test system has been dismantled.

Did you test the new release before putting it into production?

No. There wasn't time.

Did you install the server-side updates?

No. The IT manager won't allow installation of any server updates.

Other than installing the new version, did you keep everything else the same?

No, we changed a few other things too. Can't remember exactly what.

Are you sure this "new" problem never occurred with the previous release?

No. Maybe.

Can you roll back to the previous release?

No. We blew away the old data after converting it to the new format.

Well, Kris, can you tell us how to fix it?

Syndicate content