Coding Horror

programming and human factors

Programming 4 Fun

Looking for something fun to do on family night? How about a friendly game of c-jump, the programming board game:

c-jump, the boardgame

Although the prospect of a computer programming board game sounds positively stultifying, there is a rich history of computer games based on programming.

It's not a programming game per se, but we can't talk about educational games without mentioning MECC's seminal The Oregon Trail, perhaps the archetypal educational computer game.

The original Oregon Trail model was developed in 1971 by myself and two other college students when we were seniors at Carleton College in Minnesota. The three of us were completing our practice teaching in Minneapolis, and they (both math teachers) were using a computer system in their classes. I was teaching U.S. history and asked them the fateful question, "Can't we do something with the computer in my class?"

Many people who grew up with Apple IIs in the classroom have fond memories of this game. There's a great page where you can play the game in your browser through an ActiveX emulator control (IE only, obviously). This version of the O.T. is a bit fancier than the all-text version I remember, though.

MECC's The Oregon Trail screenshot

There were other educational games on the Apple II that were a bit closer to actual programming. One of those is Robot Odyssey.

Robot Odyssey, solution to puzzle 2

Robot Odyssey was about programming robots to solve puzzles. In order to do that, of course, you'd have to wire up the guts of the robot, and that meant learning about connecting inputs to outputs, and boolean logic (AND, XOR, etc). It had one of the best tutorial modes in any game I've ever played, which was critical for a game this complex. There's a modern update called DroidQuest that you can play in the browser (Java required).

The predecessor to Robot Odyssey was Rocky's Boots, which also involved programming robots to solve puzzles:

Rocky's Boots is an electronic construction set. In the program, Rocky, a boot-wearing raccoon, teaches children to build animated logic machines. Users build arbitrary logic circuits and use them to program robots in the context of an adventure game. The object of this game is to score points by making a machine to kick object targets out of a trough. The machines are composed of circuit parts that direct the flow of electricity. They are built by moving the cursor around the screen, picking up parts and hooking them together. The object targets vary in shape and color and the player must connect logic gates in such a matter that only the objects of a desired shape or color are kicked when they pass through sensors.

Rocky's Boots

Rocky's Boots was written by Warren Robinett, who also wrote a number of Atari 2600 games including the influential Adventure and perhaps most tellingly, the BASIC programming cartridge (which required the keypad controller):

atari_2600_basic_programming.jpg

There's a short interview with Warren in the book Halcyon Days that offers a bit of background on his Atari 2600 years.

The spiritual successor to both of these classic Apple II games is Cognitoy's 2001 PC title Mindrover. It takes the same gameplay concepts and expands them brilliantly into glorious real-time OpenGL:

MindRover is 'the Intelligent Robot Simulation' or perhaps you can call it a 3D strategy/programming game. This is a new genre that encompasses the depth of play found in strategy games with a new concept in player control. You get to program the intelligence of robotic vehicles.

You are a researcher on Europa, a moon of Jupiter. In your free time you re-program the rovers to race around the hallways, battle it out with mini lasers and rocket launchers, and find their way through mazes.

Once you have chosen a challenge, equip your vehicle (hovercraft, wheeled or treaded) with various sensors, movement components, and weapons. Then program the behavior of your vehicle in a graphical interface where you wire the components together and set their properties. Then let it go in the arena and watch how it does!

mindrover screenshot

Microsoft may have just launched their Coding4Fun site a few months ago, but the real programming fun started 20 years earlier.

Discussion

On the Death of the Main Menu

One of the biggest highlights of PDC 2005 was the first day keynote, when the Office 12 UI was unveiled. I don't know if people realized the significance of what we saw at the time-- but we had just witnessed the death of the main menu.

Microsoft Word 10

Microsoft Word 12

There's no "dropping down" in Office 12*; it's a context-sensitive tabbed palette interface.

There is no main menu.

That's huge. The main menu has been a cornerstone of the WIMP interface since way back in the days of the Apple Lisa. Julie Larson-Green, the PM of the office UI team, explains:

The main part of the user experience is code-named the "ribbon." It's the one place you go to find the commands that are all about authoring –creating the document, the presentation or the spreadsheet you're working on. There's no longer a stack of task panes and menus and toolbars to look through. There's just one place to look for commands.

UI innovations in Office tend to be rapidly adopted by Microsoft across their entire product line. Not only there, but in third party applications and even other operating systems. Remember the toolbar? That was unknown until it debuted in Word in the early 90's**. Now it's ubiquitous. The "ribbon" is a similar paradigm shift. Eventually we'll all be using these tabbed palettes with nary a drop-down menu in sight. I expect the traditional WIMP main menu to go the way of the dodo soon after the release of Vista and Office 12 in 2006.

* with the apparent exception of the File drop-down, but even that doesn't look like a menu in the traditional sense when you click on it.

** The MS presspass article states that this is "the most dramatic change to the way Office apps work since the introduction of the toolbar in 1997". I think the toolbar goes back much further than that! I just installed a copy of Microsoft Word 1.1a in a fresh Windows 3.1 VM image. Guess what? It has a toolbar. So does Word 2.0.. and Excel 4.0. I don't know what kind of crack those MS presspass guys are smoking..

Discussion

In Defense of Verbosity

During the fantastic Monad session at PDC 2005*, Jeffrey Snover and Jim Truher illustrated the tradeoff between verbosity and conciseness:

cp c:apples c:oranges -fo -r

copy-item c:apples c:oranges -force -recurse

Monad has a ton of aliases for common commands (eg, echo is the same as write-object), and it's smart enough to disambiguate parameters if you type enough characters. You get to choose: do I want to be verbose, or do I want to be concise?

Even UNIX tools, which aren't exactly known for their user friendliness, typically offer both verbose and concise options. Consider the excellent wget utility as an example. What the heck does this mean:

wget -m -k -K -E http://www.gnu.org/ -o /home/me/weeklog

Who knows? It could be doing anything. But if we disambiguate with the verbose parameters...

wget --mirror --convert-links --backup-converted
--html-extension -o /home/me/weeklog
http://www.gnu.org/

Suddenly it's quite plain what is happening.

People say VB.NET is too verbose like that's a bad thing. Is English too verbose? Would this post be easier to read in a court reporter's shorthand? Would it be easier to read if I dropped the vowels and the stopwords?

Compare this elegant, concise C# code..

}
}
}

.. to its VB.NET equivalent:

End Select
End If
End If

VB.NET has its problems, to be sure, but verbosity isn't one of them. Saving keystrokes while writing code is a fool's economy. Isn't that why we have these fancy IDEs? As Steve McConnell notes in Write Programs for People First, Computers Second, optimizing for conciseness is a poor tradeoff. Most code is written only once, but read dozens of times:

The computer doesn't care whether your code is readable. It's better at reading binary machine instructions than it is at reading high-level language statements. You write readable code because it helps other people to read your code.

Readable code doesn't take any longer to write than confusing code does, at least not in the long run. It's easier to be sure your code works if you easily read what you wrote. That should be a sufficent reason to write readable code. But code is also read during reviews. It's read when you or someone else fixes an error. It's read when the code is modified. It's read when someone tries to use part of your code in a similar program.

Making code readable is not an optional part of the development process, and favoring write-time convenience over read-time convenience is a false economy. You should go to the effort of writing good code, which you can do once, rather than the effort of reading bad code, which you'd have to do again and again.

The idea of writing unreadable code because you're the only person working on a project sets a dangerous precedent. Your mother used to say, "What if your face froze in that expression?" And your dad used to say, "You play how you practice." Habits affect all your work; you can't turn them on and off at will, so be sure that what you're doing is something that you want to become a habit. A professional programmer writes readable code, period.

Even if you think you're the only one who will read your code, in the real world chances are good that someone else will need to modify your code. One study found that 10 generations of maintenance programmers work on an average program before it gets rewritten (Thomas 1984). Maintenance programmers spend 50 to 60 percent of their time trying to understand the code they have to maintain, and they appreciate the time you put into documenting it (Parikh and Zvegintzov 1983).

The ethic Steve is promoting here isn't specific to any language, of course. But it certainly does skew the results in favor of verbosity-- if it's available.

* Which were evidently rated #3 right after Anders' two talks, so if you didn't go, you missed a great session!

Discussion

Everything you always wanted to know about Task Manager but were afraid to ask

Does anyone remember the Task List from early versions of Windows?

Vintage Windows Task List

From those humble beginnings comes my all time favorite windows applet, the venerable Task Manager. Task Manager was introduced with Windows NT 4.0, and although it has changed little in the intervening nine years, it hasn't needed to. Unlike virtually every other Windows OS applet of similar vintage** I still use it every day. That's a testament to how well Task Manager was originally designed.

Windows Task Manager

There are a few different ways to launch Task Manager:

  1. If you're lazy:

    Right click an unoccupied area on the task bar and select Task Manager

  2. If you're a contortionist:

    Shift + Ctrl + Esc

  3. If you love modal dialogs:

    Ctrl + Alt + Del, then click the Task Manager button or press the T key.

  4. If you're a ninja keyboard user:

    windows_key.gif + R, taskman, Enter

Task Manager has a tabbed interface, and there are a few rules applicable to all tabs:

  • Double-clicking the body of the tab area causes the tab to "expand" to cover the entire dialog area. This is particularly useful on the tabs with graphs (Networking and Performance).
  • The Options and View menus are tab-sensitive; the menu items change depending on which tab is currently active. Be sure to try these menus with each tab selected to see the various options available.
  • If explorer crashes, you can use taskman as a quick and dirty shell to restart your machine or launch a new process. Just use the File | Run and Shut Down menus.*

The Applications tab isn't a complete list of everything running on your computer, just a list of everything that has a visible main window.

taskmanager_applications_tab.png

  • It's not obvious, but you can multi-select applications on this tab. Try it! This also works for End Task and Tile/Cascade from the Windows menu.
  • Double-click an application to switch to it. You may want to turn off Options | Minimize on Use if you like doing this.
  • Don't forget the right click menu. It's the most convenient way to interact with the applications in the list.
  • Sometimes it's hard to tell how applications map to processes. Why guess when you can right click the application and select Go To Process? That will take you to the process tab and highlight the correct process.

The Processes tab is a list of everything running on your PC, whether it has a visible window or not. I use this tab all the time to scan for processes using a lot of CPU or memory.

taskmanager_processes_tab.png

  • Drag and drop the columns to re-order them; double-click a column border to auto-size it.
  • Sorting column headers is probably the single most powerful function in task manager. You can diagnose almost any performance problem by sorting the right process column!
  • The default set of process data columns is extremely spartan. I recommend using the View, Select Columns menu to turn on the optional process information. There are tons more columns to choose from, but these are the most essential for day-to-day use:
    • Mem Usage
      The "working set" of a process-- the amount of memory it is actively using right now to do whatever it is doing.
    • Peak Mem Usage
      The maximum amount of memory this process has ever used since it was running.
    • Page Faults
      The number of times this process has been forced to reload memory pages from the page file.
    • VM Size
      How much of the processes' less frequently used memory has been paged to disk.
    • Base Priority
      The priority of this process. Low and Normal are standard; anything with a higher priority than that is quite unusual and should be reserved for system processes. Note that taskman itself runs at High priority by default.
  • Judicious use of right-click, Set Priority on a CPU or I/O intensive process can work wonders to make your machine more responsive. Reducing priority is fairly safe. However, I would avoid increasing priority unless you have an extremely compelling reason to do so.
  • If you have a dual core or dual CPU system, using right-click, Set Affinity can help performance by binding a CPU-intensive process to a specific processor. That's how you avoid the "each processor is at 50% load" phenomenon. Some tasks can benefit slightly when they are stuck to a particular CPU.

The Performance tab is the ultimate "dashboard" tab. If you know what to look for, this tab can tell you everything you need to know about the health of your PC.

  1. CPU usage

    taskman_cpu_usage.png

    CPU usage is the one graph that doesn't need a lot of explanation. It will show one graph per CPU, so it's a good way of verifying that your multiple CPU system is load sharing appropriately. You can also add a red kernel time line to the CPU graphs via the View, Kernel Time menu. That's a measure of how much time the CPU is spending servicing low-level driver requests (eg, busywork) instead of running code.

  2. Page File usage

    taskman_pagefile_usage.png

    Apps tend to request a lot of memory-- more than they use at any given time. The OS will trim the less frequently used memory by writing it to disk in the page file. Page file usage is typically not a concern except in extraordinary cases; it's the commit charge you have to worry about.

  3. Totals

    taskman_totals.png

    A count of all the resources in use on your PC: processes, threads, and handles. Not terribly helpful; it's better to drill down on this data via the processes tab.

  4. Physical Memory

    taskman_physical_memory.png

    System Cache tells you how much memory is being used as a disk cache, eg, to avoid accessing the physical hard drive. There's a delicate balance between System Cache and Available Physical Memory. You want a reasonable amount of free memory, but free memory is also wasted memory-- it should be utilized as disk cache whenever possible.

  5. Commit Charge

    taskman_commit_charge.png

    Commit charge is the single most important section of the performance tab. It's the total amount of memory in use by all applications, including memory that has been temporarily paged to disk. If the peak commit charge is greater than the physical memory in your PC, your PC is running out of memory and thrashing. If it happens rarely, you're OK, but if it's a frequent occurence, it's time to get a memory upgrade. And god forbid you ever reach the commit charge limit. I guess then it's time to upgrade to a 64-bit OS.

  6. Kernel Memory

    taskman_kernel_memory.png

    Every application has a certain amount of OS housekeeping overhead. Most of it can be paged to disk if necessary, but some has to be in memory at all time. These numbers are basically trivia since they're so small relative to the 512mb or 1gb of memory in a modern PC.

The Networking tab is the newest addition to Task Manager, but it's also the most disappointing.

taskmanager_networking_tab2.png

  • By default you'll see total bytes (green). You can break out bytes received (yellow) and bytes sent (red) via the View, Network Adapter History menu.
  • The graph is always displayed as a percentage of network utilization, which I find incredibly annoying. I wish there was a simpler graph that showed bytes or kilobytes on the axis instead of percent utilization. We can't change the graph, but we can use the View, Select Columns menu to turn on the optional columns Bytes Sent Per Interval and Bytes Received Per Interval.

    taskmanager_networking_tab3.png

    Divide by 1024 and we've got kilobytes per second throughput for that network card.

Yeah, there are better task management applications, but you have to admit-- for a nine year old bundled application, ye olde Task Manager is pretty kickass. I took a quick look at Task Manager in the latest pre-beta 2 build of Windows Vista from PDC 2005, and I didn't see any obvious differences. Here's to another 9 years of glorious Task Management!

* the "Shut Down" menu is not shown on the Task Manager window when accessing machines over Remote Desktop. However, you can shut down machines remotely using Ctrl+Alt+End to bring up the Windows Security dialog which has a Shut Down button.

** Charmap or WordPad, anyone? I didn't think so.

Discussion

When Email Goes Bad

It's easy to fire off an email with barely any effort at all. And that's exactly how much effort goes into most emails: none. Ole Eichhorn's Tyranny of Email offers a succinct set of guidelines to avoid thoughtless email abuse:

  1. Never criticize anyone in email. Avoid technical debates. Use face-to-face meetings or phone calls instead.
  2. Be judicious in who you send email to, and who you copy on emails.
  3. Observing some formality is important.
  4. Don't hesitate to review and revise important emails.
  5. Remember that email is a public and permanent record.

Ole published another article, Tyranny Revisited, with some commentary on the response to his original article.

43 folders recently published a great article on writing sensible email messages:

  1. Understand why you're writing: what's the goal?
  2. Assume no one will read more than the first two sentences of your email.
  3. Write a great subject line.
  4. Fit it on one screen with no scrolling.
  5. Ask for what you want.

Similar rules apply to instant messaging, telephone, and even face-to-face conversations. The key difference is the amount of effort required for each communication method: the easier it is, the more you need to consider before doing it.

Of course, the real art is knowing when to escalate from IM to email, from email to face-to-face, and when to drop the ultimate communication A-bomb: calling a meeting.

Discussion