This year my wife decided to make multi-colored Christmas light strands by changing the individual light bulbs on solid-colored strands. The task seemed simple, if tedious, enough:
We followed this process, and after an hour we were ready for step 4. Veteran Christmas decorators know what happened next.
Two bad strands.
Christmas light bulbs are wired in series, meaning that one bad bulb will prevent the strand from lighting. For one more hour, we worked up and down the faulty light strands, looking for the bad bulb. We checked each bulb for a tight fit. Then we pulled each bulb out, furiously examining the connections, occasionally tweaking them. Every time we'd test the strand, we did not see any lights. Finally, we were able to fix all the strands. In total, we spent two stressful hours to create three multi-colored strands.
That night I laid in bed thinking about our experience. When we started, I felt great! We had an efficient plan. We would do the jobs in batches: finish one task (pulling out lights) before moving onto the next (putting in new lights). With no task-switching, it felt like we'd get done in no time. Unwittingly, we had followed the waterfall process of doing Christmas lights.
Our downfall, and the waterfall's downfall, was not knowing where we introduced the errors. In that second hour, testing the lights like crazy but never certain that we were making things better instead of worse. In both hours, we were so busy that our perceived productivity was high, but our actual productivity does not. We did not introduce any testing until the end, like a software team that does not test until development is done.
I realized an agile, test-driven development process would be the way to go. We would introduce regular testing into our process. Instead of time-boxed iterations we used lightbulb-boxed iterations. On the next set of strands, we stopped and tested each of the strands every three bulbs. While we had a lot of task-switching, we also had a high degree of certainty. Each test, either the whole strip worked, or one of the last two changed bulbs was faulty. Progress was slow but steady. We finished and had three working strips in 90 minutes.
In the waterfall process of Christmas lights, we sped through the bulb changing (development) but got hung up in test. With the agile approach, our bulb changing (development) time increased 50% but the final test was a breeze. In each case, we made the same total number of mistakes, but in the agile approach we caught and corrected them faster.
Test-driven development is a powerful concept. In the past several months, it has made me a better software developer. My wife's Christmas lights showed me how powerful agile techniques are outside the compiler.
Last night #5 Yuengling squared off against #4 Stoppage Time, in a rematch of their regular season tilt won 3-1 by Stoppage Time. Yuengling had to put away their traditional green jerseys as we were the lower seed and Stoppage Time also wears green. It was pretty strange to see us all in white. I yelled "come on green!" a few times before catching on!
Yuengling dominated early, scoring an early goal and maintaining good ball possession and pressure. Lawrance chipped a beautiful set shot to the upper right hand corner for what should have been a 2-0 lead, but their goalie Arnett just barely tipped the ball off the post, probably the best save of the game. After the ensuing corner kick, Stoppage Time went on the offensive, culminating with a goal off of a corner kick of their own. Immediately the halftime whistle blew. 1-1 tie.
We came out of the gates ... flat ... and Stoppage Time dominated in all aspects. They had several good scoring opportunities but did not capitalize. Eventually the tide turned and things were more even. I started going over overtime and penalty kick scenarios in my head. Then, somehow, we forced a goal on a shot from a terribly narrow angle. With only a few minutes remaining, this lead should be enough to seal the deal.
The Stoppage Time offensive resumed! For the rest of regulation, there was nothing but offensive pressure from them. They got a free kick a few yards outside of the 18 yard goal box, and I screamed for a 4 man wall to guard the near post. I set myself up towards the far post. Incredibly, the shooter looped the ball around the wall and towards the near post! I got my hands on it but not enough, coughing up a rebound. I dove for the rebound. Rolling, with my hands on the ball again, an opposing player was winding up for a big kick. I pulled the ball to my chest and ended up rolling into him, and he crashed over top of me. Phew.
The referee signaled there was one minute remaining. Stoppage Time got another corner kick. The kicker blasted a low, knuckling shot towards me, and I barely got my hands on it and pushed it out. Unfortunately, right back to him! He took another low knuckling shot, and again I could not contain it. It bounced around the goal area. A Yuengling player cleared the ball to the sidelines, intercepted by the opposition again! But, they failed to settle the ball and it bounced out of bounds. And then we heard it -- that sweet, sweet sound of the game over whistle!
It took one playoff game for us to match our regular season win total! In typical Yuengling fashion, we will face the #1 seeded team in the 2nd round. As far as I remember, this is the exact script we follow almost every season. The only difference this year is that the #1 team is not our nemesis, the Lions but rather FC DTWC, a strong team but also the team we tied in the regular season finale. Our next game should be interesting. We have next week off, so you'll have to wait two weeks for the next one!