The
saga of the Webcam continues. At least it's back on its perch.
Here's what I found when I got to my office a few minutes ago:
And here is what the Inner Drive Webcam saw as it teetered, tottered,
and tumbled to the floor of the office. At 5:53pm Central time, all was fine:
Then, suddenly, the mounting began to give way. The first shock came at 5:54; the
second, at 5:57:
The mounting held for a while; here are shots at 6:15 and 6:30:
The end, when it came at 6:33, came swiftly. A jolt at 6:31, another at 6:32, then
at 6:33, blackness:
Until, bleary eyed and stunned, it woke to a changed world at 7:30 the next morning.
The final shot is 9:00am, about the time I discovered the horror of the fallen Webcam:
But, gentle readers, the Webcam is back up. At this writing, here is the image,
in all its properly-mounted glory:
(Your guess is as good as mine what it sees tomorrow morning.)
Sigh.
Astute readers will gather from the preceding post that I am out of the office for a couple of days. And pessimists will agree that, if something were going to go wrong in the office, it would go wrong the day I left. Pessimists: rejoice! The Inner Drive Webcam has decided to add a new page to its history:
Now, as nearly as I can figure it, you're looking there at the back end of the computer that hosts the camera (highlighted below), upside-down. I'll have to review the archives on Saturday to figure out exactly when this happened. And I'll have to review the method I'm using to secure it to the window.
For a couple of years, Inner Drive has
had a webcam pointing
out the window. We've moved twice since the webcam first went online. From time
to time, we've adjusted the webcam slightly. And, every so often, the webcam adjusts
itself.
For example, the first cam image is from when we left the office last night, and
the second from when I woke up this morning:

(The images are displayed at half-size, but you can view them at full-size by saving
them from your browser. You'll notice that they have timestamps, which are in Universal
time.)
The poor webcam was lying on the floor of the office covered by the box upon which
it had previously sat. See how it sits precariously in this photo? Imagine it now
in a heap under the chair by the window.

So, since we had to move it anyway, we decided to rotate it south 90 degrees, to
this angle:

For those interested in history, here is what the image looked like yesterday during
the day, and at 6, 12, and 18 months ago, respectively:


And finally, here is what the Inner Drive Technology World Headquarters looked like
in October 2004 and October 2003:

(Yes, the image on the right is of my living room.)
Note: I didn't realize when I started this post that today is the second
anniversary of the Webcam. As a special bonus, here is the very first Inner Drive
Cam picture ever, from 17 December 2003 at 1:28 pm CST (19:28 UTC):

I've finally added an explanation of Evolutionary Delivery to my corporate site. I wrote this as part of a proposal to a client in September, and for reasons that passeth understanding, I neglected to publish it online.
By the way, I write software for a living, so if you're reading this and realize you need a small, agile development team for a .NET project, send
us a message.
A code smell happens when a piece of software code looks like there might
be something wrong with it, but you can't quite tell what. You use the smell to
figure out where the bad code is hiding. Martin
Fowler has devotes an entire chapter of
Refactoring to code smells.
Here is an example, from a class that returns configuration information:
public string Read() { ... }
public double ReadD() { ... }
public int ReadN() { ... }
public string ReadString() { ... }
What's wrong with this code? Several things:
- It does the same thing four times.
- Having two similar methods that appear to return exactly the same data raises a
red flag, because you don't know from looking at them why they differ but you feel
like they differ for a reason.
- Despite the code's appearance, it actually offers no guarantee that the data requested
will be of the correct type, only that the data will have a particular type.
- if some random piece of code requires a data type it doesn't support, you'll have
to add yet another method to the class, or change the returned data to suit what
you need, neither of which makes a lot of sense.
This code came from an ancient, functional-procedural outlook in which the type
of data returned actually matters. Object-oriented design cares more about what
the data represents. In other words, this code is like multiple different filler
tubes on your car, one for each grade of gasoline.
There's more. A little farther on, we find these methods:
public int ReadArray(string, ref String[]) { ... }
public int ReadArray(string, ref int[]) { ... }
public int ReadIntArray(string, ref ArrayList) { ... }
In all, there are 14 "Readtype" methods on this class, some that
return the data sought, others that return a status indication and pass the data
back through a by ref parameter.
And, of course, since this is in a fundamental class, none of these methods has
fewer than 5 references to it in the application, and some (like ReadN) have
34, making refactoring unusually difficult. I'll post again when I figure out how
I'm going to do that.
Addendum to my previous reading list.
I'm now reading Microsoft's Framework Design Guidelines
, written by the guys who wrote the .NET Framework.
Add this to my list of recommended books.
I've just finished Edward Tufte's essay, "The Cognitive Style of PowerPoint." It is now on the Inner Drive Technology required reading list:
Explanations of these choices to follow shortly.
Yesterday at the gym's coat check, I got claim check 404.
The coat-check guy didn't find this nearly as funny as I did.
Even more funny—to a software nerd, anyway—was that when I gave him check #404 after working out, he found my coat.
One can imagine other possibilities. But 404 is the best, I think.
Read, understand, and then fix your compiler warnings.
Compiler warnings let you know that you've either done something wrong, or you've done something non-standard. Either way, ignorning compiler warnings shows a lack of discipline and skill; it's something like ignoring big red "warning" signs in real life.
I'm working on a .NET solution that, when last compiled, generated over 60 warning
messages. A couple of them I put in to let other developers know about problems
I found, but most warned about things that actually needed to get fixed.
For example, the following line of code:
if (comboBox.SelectedItem == "Do stuff")
generated the warning, "Possible unintended reference comparison; to get a value
comparison, cast the left hand side to type 'string.'"
In other words, the if statement was evaluating whether the object comboBox.SelectedItem
was the same object as the string "Do Stuff," which is an impossibility.
So the comparison would always fail, making it look like the feature was
failing. Yet the compiler warned the developer about the problem, and even said
how to fix it.
If you're wondering, the corrected line looks like this:
if ((string)comboBox.SelectedItem == "Do stuff")
Anne and I attended the taping last night of Wait Wait — Don't Tell Me!, the NPR News Quiz. It airs Saturday.
If you don't listen to the show, tune in, and find out how to get Aerosmith and Kenny G to play the same gig, among other things.
Note: You may have seen this post earlier. In a continuation (recurrence?) of earlier problems, Das Blog ate the post about an hour after it went up. Grr.