There’s a programming meme featuring the Looney Tunes characters of Wile E. Coyote and the Road Runner. These characters are locked in a never-ending chase, where the Coyote seems to come close, but not quite catch the speedy bird. In the meme itself, it shows the Coyote running off of a cliff due to his misuse of the do / while
iteration construct, whereas the Road Runner stops short because he presumably used the while
iteration construct.
In this post, I’ll be implementing the meme using C#. I bet the results will surprise you.
The Meme
If you haven’t seen the meme, here it is.
Chase Assumptions
Before we code anything, we have to lay down the ground rules for this chase between the Road Runner and Wile E. Coyote.
- There is a single runway that both the Road Runner and Coyote will share. Its length is arbitrary.
- The cliff appears at the 90% mark on the track.
- The Road Runner starts one “tick” in front of the Coyote, and will run until he reaches the cliff, at which point he will stop. He will be using the
while
loop construct. - The Coyote starts one “tick” behind the Road Runner and will run until he reaches the cliff, at which point he will stop. He will be using the
do/while
loop construct. - If the Coyote and Road Runner stop at the cliff, then the Coyote will have eaten the bird.
The Code
For my code sample, I am using .NET Core and the ShellProgressBar library to animate the progress of the Road Runner and Wile E. Coyote.
using System;
using System.Threading;
using System.Threading.Tasks;
using ShellProgressBar;
namespace Acme
{
class Program
{
#region Ascii Art
private const string OnYourMarks = @"
....
,''. : __
\|_.' `: _.----._//_
.' .'.`'-._ .' _/ -._ \)-.----O
'._.'.' '--''-'._ '--..--'-` .==,_
.'.'___ /`'---'. / ,-'` .===,_`\
snd _<__.-._))../ /'----'/.'_____:'. .====,_ ` \ .====,__
\_ : \ ] : '. --- .==-,`~. \ `:`.__,
\___: \\ : '. --- `~~=-. \ /^^^ ...beep beep!
: \\__ : .' --- `~~=. \ /
:_______________|__]__________: .' `~. \ /
.' __ '. :.' ~. \____./
.' .' '. '. jgs `.=====)
.' .' '. '. ___.--~~~--.__
.' .' '. '. ___\.--~~~ ~~~---.._|/
_.' .'______________'. '._ ~~~"" /
[_0______________________0_]
";
#endregion
public const int Runway = 1000;
// the edge is at 90% of our runway
public const int TheEdge = (int) (Runway * .9);
// how fast are they running
public const int Pause = 2;
static void Main()
{
Console.Write(OnYourMarks);
Console.WriteLine();
Thread.Sleep(3000);
using var cliff = new ProgressBar(Runway, "The Cliff", new ProgressBarOptions
{
BackgroundColor = ConsoleColor.Black,
ForegroundColor = ConsoleColor.DarkGreen,
});
var roadRunner = cliff.Spawn(Runway,
"Road Runner (Accelleratii Incredibus)",
new ProgressBarOptions
{
BackgroundColor = ConsoleColor.DarkBlue,
ForegroundColor = ConsoleColor.Blue,
});
var wileECoyote = cliff.Spawn(Runway,
"Wile E. Coyote (Carnivorous Vulgaris)",
new ProgressBarOptions
{
BackgroundColor = ConsoleColor.Red,
ForegroundColor = ConsoleColor.DarkRed,
});
// beep beep -- road runner gets a head start
roadRunner.Tick();
Task.Run(() =>
{
// roadrunner runs
while (roadRunner.CurrentTick != TheEdge)
{
roadRunner.Tick();
Thread.Sleep(Pause);
}
});
// Wile E. Coyote chases
Task.Run(() =>
{
do
{
wileECoyote.Tick();
Thread.Sleep(Pause);
} while (wileECoyote.CurrentTick != TheEdge);
});
for (int i = 0; i < Runway; i++)
{
cliff.Tick();
Thread.Sleep(Pause);
}
if (wileECoyote.CurrentTick == roadRunner.CurrentTick)
{
Console.WriteLine("🍗 Yum.... Road Runner for Dinner! 🍗");
}
}
}
}
The Animated Results!
In the spirit of cartoons, I decided to add some animated suspense. Let’s run the code and see if Wile E. Coyote will finally get that elusive Road Runner.
It looks like Wile E. Coyote has Road Runner for dinner!
Conclusion
The meme on face value is funny, but it implies the use of do/while
loops can be an issue for developers. In reality, it is about the logic in an application, and in the case of the meme, the implementation is just fine. The only time the Coyote would run off the cliff is if both he and the Road Runner were already standing on the edge and the Coyote decided to jump off.
It’s easy to poke fun here, and this post is very tongue-in-cheek, but the biggest takeaway is that language constructs aren’t inherently good or bad; it is about how we use them within the context of our applications. What did you think? Let me know in the comments.