06 February 2009

Failed reasoning by an Ivy League Grad Student; Engineering and Approximation

Let me babble for a little bit...

There was an extended power failure in Princeton last night---for two hours, all three power inlets to the boro went down, and so all the uninterruptible power supplies drove themselves dead. While the CS department's servers were hooked up to a secondary generator, the servers for my research group went down.

After power was restored, our machines booted back up, but in the incorrect order. One of the other students in the group had to go visit them to remount NFS partitions, make sure they all came back up, etc, etc.

While he was down there, he observed a chirping noise. Looking around underneath tables and racks, he found the culprit: an uninterruptible power supply that wasn't plugged into the wall, and had nothing plugged into it. Judging by its position, he decided that this was a power supply for a server that had been of commission for at least a decade. He reasoned that it took about ten years for the minute inefficiencies in this UPS to drain the battery.

But, the damned thing was still chirping. Looking around, he couldn't find a free plug, and so he couldn't restore power to the UPS. "How can I make this stop chirping?" he asked himself.

His solution amazes me: he plugged the UPS into itself.

Now, clearly, the UPS isn't going to charge, and he doesn't dispute that. He argued, however, that this should be enough to fool the UPS into thinking that it was charging. In other words, he conjectured that the UPS chirps iff it does not have wall power; he was wrong, because he assumed the UPS engineers had made an approximation they had not. In actuality, the UPS continued to chirp. This is because the UPS chirps iff there is a negative change in the charge of the battery. It takes some time to measure this change, and this is why UPSes will chirp for a short while after you plug them back in.

Why do I bring this up? Because it allows for an interesting analysis of approximation, and maybe we can pull out some principles of design. What semantics does the chirp noise carry? The chirp noise should denote battery discharge. Under the assumption that the UPS can always charge the battery as fast as it is discharged when plugged in, the UPS would stop chirping when plugged in. The question is: do you want to measure the real scenario, or can you get away with measuring symptoms of the scenario?

Engineering is the fine art of approximation. Approximation is so ingrained into our reasoning that we have mathematical operators to describe it: x << y means x is significantly smaller than y; x -> y means that as the value of x comes arbitrarily close to y; epsilon denotes an arbitrarily small number; we say a function f is O(g(x)) to mean that as x gets arbitrarily large f(x) is bounded by some constant times g(x). The meanings of significant, arbitrary, and some vary wildly by situation.

Engineers make jokes about it too: a horse is a sphere if it makes the numbers easier; 2+2==5 for very large values of 2. Approximation is critical, but only where appropriate.

In the UPS example, the charge of the battery can be measured more or less directly. In many other circumstances, the real scenario is hard to measure, but symptoms of it are easily measured, and an approximation can be computed from those measurements. A couple examples come to mind:

  • You use a compass to find North, but it actually tells you the direction to something that is mostly north of you and very far away. Sailors have shown that for navigation within a few hundred miles, this is perfectly sufficient.
  • It is difficult for a robot to measure its exact position in a room, but it can easily measure how much each of its wheels has moved and then deduce its relative position via dead reckoning. For short distances, the error of this approach is negligible.
  • People say you should change your oil every six months or 6,000 miles. In reality, it's a question of the quality of the oil (how much crud has accumulated?), not how long or how far you've used it. Oil is cheap and engines are expensive, so this method is successful.
  • When structural engineers design a building, they use a safety factor---building every piece n times as strong as need be---to account for variation in manufacturing, material aging, and unforeseeable events. Steel is cheap and wrongful-death lawsuits are expensive, so this method is successful.
  • Software engineering preaches: it's more important that the software works than that it works efficiently; instead of writing in machine code, we use high level languages that favor programmer time over execution time. Programmer time is expensive, but faster computers are cheap, so this method is successful.
So, next time you design something, take another look at the approximations you are making. More importantly, look for approximations that you are not yet making. So long as you are conservative enough to ensure your approximations are right enough, they can save you a lot of effort.

Maybe your robot can't read GPS, but there are other ways it can geolocate. Maybe your software cannot successfully identify some event, but if it can be right more often than not, it can pass the final say onto a human operator. Possibilities are endless.

01 February 2009

Proposal for a future Interstate Rail Network

From The Transport Politic:

The transport politic blog has run the numbers and made a proposal for a high-speed train network for the United States. I think they've done an incredible job, and so I want to mention them here. Their plan is based upon a few pillars:
  1. This network would be funded 50--90% by the Fed; compare to roads and highways that are funded 80--90% by the Fed.
  2. This funding would be part of the expected economic stimulus plans. In this respect, it sounds to me like a big WPA project instead of a bailout.
  3. A new national authority (which they call NatTrack) will be responsible for acquiring land, building and maintaining tracks, and renting those tracks to service providers such as Amtrak.
  4. They identify the ideal route as one that is (a) shorter than 500 miles, and (b) between two population centers of 100,000 or more. These numbers were chosen as they [a] typically beat an airplane in overall travel time, and [b] have enough potential customers to maintain the route.
  5. The main network features high-speed (150 mph) trains; this is supplemented by low-speed (70--120 mph).
  6. Their route choices were computed mathematically, under some well-defined assumptions. At the end of the article, they give numeric scores for each route to justify their choices.
Again, this is excellent work. I encourage you to read their article. I hope this has a chance.

Update to pipemiter.rb

Last week I wrote about a simple script to miter pipes. As soon as I wrote it, I realized about a hundred ways it could be improved, and about a hundred new ways it could be used.

My first observation was that the old version would fail if the cutting template was too large to fit on one page. To solve this, I added pagination support---the image will be split across multiple pages, and alignment marks will be drawn at each corner so they can be stitched back together.

Next, I noticed that real pipes have some thickness, i.e. the inner diameter might be significantly smaller than the outer diameter. As a result, you can now specify an inner diameter, and it will draw a gray curve alongside the black curve of the outer diameter. This can make it easier to miter thick tubes.

Also, I realized that one often wants to miter several tubes against one. In this case, you don't just measure how to cut the smaller tubes, but also where the smaller tubes meet the larger one. For this reason, the software will now draw a guide for the large tube as well.

Beyond that, there are numerous little changes to make it easier to use or more fool-proof.

The script is now in three files:
  1. pipemiter2.rb - the main executable,
  2. units.rb - handles unit conversion in a not-too-painful way, and
  3. postscript.rb - a library for drawing postscript images.
Save all of these files to some directory. Like before, we can either invoke this program from the command line, or in interactive mode.

You specify a pipe scenario as a single center pipe (i.e. the one that doesn't get mitered), and one or more radial pipes (i.e. the ones that get cut to fit the center pipe). The center pipe is simply specified as its diameter (or equivalently, its circumference or radius). Each radial pipe is specified as 3-D polar coordinates relative to the center pipe. The characteristics of the radial pipes are:
  1. Its (outer) diameter (or equivalently, it's circumference or radius);
  2. Optionally, its (inner) diameter;
  3. Its latitude, i.e. the angle at which it meets the center pipe, where a latitude of 0 means along the equator, and a latitude of +/- 90 means at the north or south pole;
  4. Its longitude, i.e. the angle around the center pipe, which defaults to 0; and
  5. Its projection, i.e. placement along the length of the center pipe.
That can be complicated, so lets go through a few examples. I'm going to write these examples in command line format, but if you don't specify any command line arguments it will go into interactive mode.

First, the example from my previous post: two toilet paper rolls (1.75" diameter) meet at a 30-degree angle. All I need to specify is the center pipe, and the diameter and latitude for the radial pipe:

$ ./pipemiter2.rb 1.75 1.75 30 >eg1.ps

Notice the output is more elaborate than last time. In particular, it's now a two page document. The first page shows the cutting profile, and then second page shows the profile on the pipe that you don't cut.

Let's try something more complicated. Suppose you wanted to build a sort of tripod-like thing. You have a center pipe 9-inch in circumference, and you have three 2-inch-diameter radial pipes. Each radial pipe meets the center pipe at a 60 degree angle, and each is evenly spaced along the circumference of the center pipe. Then you could type something like this:

$ ./pipemiter2.rb 9in-circ and 2in 60 and 2 60 by 120 and 2 60 by 240 >eg2.ps

There are a few things to note about this line. First, it specifies the center pipe (9in-circ). Next, it specified the three radial pipes: 2in 60 by x. The word and goes between each pipe specification, but is completely optional. Each pipe is specified as its diameter (2in), it's latitude (60), and its longitude (by 120, by 240, etc). The output file has four pages---a cutting template for each of the radial pipes, and then an alignment template for the center pipe.

So what's up with the units? Units are optional, though I often write them for clarity's sake. Diameter units default to inches, but could also be mm-circ (millimeters of circumference), cm-rad (centimeters of radius), ft (feet), etc. Length units default to inches, but could also be mm, cm, m, ft, etc. Angle units default to degrees, but could also be radians. Once you use a {length, diameter, angle} unit once, all future {length, diameter, angle} units default to that unit, just to save some typing. When in doubt, type the units.

So far, we've explained units, diameters, longitude, and latitude. What about projection and inner diameter? Notice that, in the previous example, the center points of each radial pipe all lined up along the equator of the center pipe. The projection parameter moves the center points up or down the length of the center pipe relative to the equator.

For example, suppose you have a center pipe of 9-inch-circumference, and want to attach five 1-inch-diameter radial pipes to it. Each of the radial pipes has an inner diameter of 0.5-inches. Next, suppose that the pipes should be connected at 60, 30, 0, -30, and -60 degrees, and that there should have a projection of +0.4-inch, +0.2-inch, 0-inch, -0.2-inch and -0.4-inch, respectively. Enter the command,

$ ./pipemiter2.rb 9in-circ \
and 1in id 0.5 60 by 0 up .4 \
and 1 id .5 30 by 72 up .2 \
and 1 id .5 0 by 144 \
and 1 id .5 -30 by 216 down .2 \
and 1 id .5 -60 by 288 down .4 \

The backslash character tells your shell that the command will span multiple lines. For each of the radial pipes, I use the id .5 command to specify the inner diameter of the pipe.

Example of pipe mitering, template
When you look at the output, you see that each cutting profile additionally has a gray curve. This gray curve is the shape of the miter along the inner diameter of the pipe---it gives you a few more hints of how to grind the pipes to meet perfectly. Also note how, on the sixth page, the inner diameter is drawn on the alignment guide. The projection is specified using up .2 or down .4, and causes the center of each pipe to move up or down the length of the center pipe on the alignment guide.

Example of pipe miteringIn case your wondering, that last example looks like this and this.

And that's it. Now you can specify the many-pipes-meet-one scenario, and have cutting and alignment guides automatically generated. This can make mitering pipes much easier for you.

Also of note is that this is not limited to mitering pipes. I've realized that it can be used to make paper/cardboard models, and that those models can be used as molds for plaster or concrete. I'll talk about pipe sculptures in a future post.

Related: Commenter Flemming gives a link to a similar online tool.