Schmonzcast #17: I’m proud to have been a speaker at this year’s Pittsburgh Perl Workshop, a two-day conference for fellow practical-minded Perl programmers. As one who has striven to code in a modern way — TDD, expressive objects, type-checking, and the like — in a non-modern environment, I’m sensitive to Perl being pigeonholed. So it was gratifying to see talks about familiar and timeless ideas (systems programming, asynchrony, inversion of control, simplicity, automated testing) as well as envelope-pushing new ones (everything Ingy said, native-extension performance, high-performance serialization). I also appreciated getting to meet the author of Higher-Order Perl and help him set up an ikiwiki to play with.
My talk was half explication, half topical demonstration: on Saturday morning we learned about Ingy’s new Swim format, and here I was on Sunday morning attempting to live-code ikiwiki support for Swim input. Would I get it working? Would I be able to give a demo? Would I eventually come to understand
mjd’s suggestion that I sing as I code? Here’s the full screencast of my presentation (or watch on YouTube).
In When I might not TDD, I posed myself the following question:
If I’m trying to be effective and efficient, when wouldn’t I practice TDD?
In response, I enumerated degenerate cases, false negatives, and conjectures, but was unable to come up with anything simultaneously true and nontrivial. Carrying out Alistair Cockburn’s Elephant Carpaccio exercise yesterday uncovered an answer I had forgotten.
In How to efficiently learn a programming language, I noticed early on that not doing TDD was probably slowing me down. So I tried adding it, started making progress and having fun, reversed my performance problem, finished early, and got to help my neighbor.
Early in Elephant Carpaccio, my “Coaching in an Agile Context” class partner and I noticed that doing TDD was probably slowing us down. So we tried removing it, started making progress and having fun, reversed our performance problem, finished early, and got to chat for a bit.
I’m relieved to know that when the environment produces a signal to consider not practicing TDD, I’m able to receive and act on it. This indicates my strong feelings about the practice are truly a matter of context, as I hope they remain. For your reference and mine, the forgotten context where I probably wouldn’t TDD is: tiny projects.
Apparently I’ve even forgotten that I remembered that context just fine in When is refactoring a good decision?. At least I still remember that my forgetfulness is one of the reasons I prefer to test first.
I’ve lost over 30 pounds since this project began in early 2013. This morning, when I weighed in, I saw a number that used to mean
- I’d been eating a little too poorly for a little too long,
- I needed to strictly avoid carbohydrate for a week or so, and
- I could expect to snap right back to my healthy weight.
Seeing this number now means
- I’ve been eating very carefully for a long time,
- I’m at my lowest weight in over five years, and
- I’m finally within striking distance of my goal.
Agency and patience
My weight has decreased so slowly, and retrogressed so frequently, that I’ve sometimes doubted my ability to bring about the desired result. But I felt confident enough in my mental model of my metabolism — and certain enough that other diets would serve me less well — to stick it out.
For a variety of reasons, I haven’t been strength training for several months. One reason is that my easily enraged sinuses have been angrier more often, disrupting breathing (mainly when I’m trying to sleep) and general functioning (when I’m trying not to). Turns out I have a significantly deviated septum, which, along with a couple other longstanding nasal demons, will be surgically corrected in a week and a half. I expect to be useless for about a week, in exchange for which I hope to be much better at breathing, sleeping, and functioning for the rest of my life.
One new form of exercise lately has been cycling to my local coworking space a few times a week. It’s not much, but it pretty immediately feels good to do it.
How I feel
- Pants and t-shirts fit much, much better
- I’m wearing nicer clothes, including some new ones, because they’re comfortable now
- My face has progressed another stage, now looking almost exactly like my face
- My belly no longer feels like a foreign object that keeps getting in the way, but merely a slightly oversized version of my own belly
- Bekki and I hiked for a couple hours with dogs through hilly terrain, and I had plenty of energy the entire time
- I hadn’t been put off by the mere idea of going hiking for a couple hours
- I’m excited to once again be physically comfortable with exercise, and to be able to concentrate more on activity and fitness than on weight per se
If you want to lose weight like I have, you need to do all the things I’ve done, in case any of them (alone or in combination) are responsible for the outcome. Go live with your partner, get a dog, quit your job, ride your bike now and again, and everything else in this post. And if none of those changes winds up helping you lose weight, hey, I’m sorry, that’s really unfortunate!
To develop working, valuable software, we expend time and decisions. In this context, a good decision is one which helps us deliver more value with our time. When might refactoring be a good decision?
What’s refactoring for?
I see refactoring, above all else, as a tool for managing risk.
Software development is naturally rich in risk. If we accept that it’s worth doing, then we’re accepting some amount of risk. For all but tiny projects, the greatest risks are likely:
- Making undesirable changes that go unnoticed until fixing them is surprisingly expensive
- Making desirable changes that seem worthwhile until implementing them proves surprisingly expensive
TDD can help us control (1) and — at no additional cost — affords us the option of refactoring, should we want to. And if we seek to control (2), I contend that we should want to.
Straw man: never stop refactoring!
Let’s say we not only put stories whose only purpose is refactoring on the backlog, but we’ve got lots and lots of “refactoring stories”, and we prioritize them over everything else. We’ll have maximized the number of possible future changes that are easy for us to make, but we’ll never get around to making any of them.
Straw man: never start refactoring!
Let’s say we not only don’t ask permission to refactor, we simply never refactor. We’ll have maximized how much time we’re working on changes motivated solely by business value, but we’ll have driven up two averages: the cost per change, and the risk of greatly underestimating the cost per change. Even if we accept that we’ve taunted Hofstadter’s Law.
Who decides to refactor?
Illustration by Rebekka Dohme.
I see developers bee-ing best positioned to decide whether, when, and how to refactor.
I don’t see that the “value” of refactoring and the “value” of software’s user-visible behavior can be measured along commensurate axes. The latter is what we’re here to do. The former is a way to improve our chances of doing it. The latter is best judged by the folks who rely on the outcome of what we make. The former is best judged by the folks who rely on the process of what we make.
When is refactoring a good decision?
If we agree that managing the risks of software development means mitigating its inherent variability while collecting just enough options along the way, then refactoring is likely a good decision when:
- Developers choose it
- Its intended scope is to clear a path in front of the desired change
- Its intended effect is to deliver the desired change faster (or at least not much slower, and then to deliver future changes faster)
After some months of judicious and opportunistic refactoring (more or less depending on context), here are some trailing indicators that you’re reaping the benefits:
- You rarely wish an estimate didn’t have to be so large
- You almost never feel the need to fudge an estimate
- You almost always get what you expected when you expected it
In software development, where risk management is a fact of life, refactoring is one of the most powerful tools at our disposal. Wielded wisely, it helps us more predictably deliver more value with our time.
My opinions generally derive from my experience (and, stubborn as I am, little else). The expression of this particular opinion is better for my having encountered the following expressions:
“If you want to estimate little things, you have to refactor.” — J. B. Rainsberger. 7 minutes, 26 seconds, and the Fundamental Theorem of Agile Software Development (Øredev 2013).
“Do not taunt Happy Fun Ball.” Saturday Night Live (1991).
Our hearts do in dark forests dwell.
Each feeling, choosing, kernel core
lives in a roughly-tangled dell,
a wilderness of soul and spore.
Each forest lives, each forest grows,
unfurls through time our destinies.
Alive with buzzing thoughts, each glows,
— Andrew Hamilton, “Akrasia Forest”
I’ve always wondered — sometimes more, sometimes less — what my life might become. Nine years ago those wonderings led me to the house and grave of my favorite composer. The past few months of leisurely introspection have encouraged me again to wonder more. When the past week found me within walking distance, I went for a return visit.
I brought my changed self. Since Medtner’s resting place last observed me, I had not merely learned to play some and analyze some of his music, I’d finally composed some I was proud to call mine. On the off chance that wouldn’t suffice, I also brought flowers. Then I cued up my recorded performance of his Sonata-Reminiscenza, sat at the foot of an immense tree, and marveled at the life Medtner lived while making the music he made. Was the former a necessary precondition for the latter, or merely incidental? Are my preconditions likely similar to his? If I’m to write my music, what kind of life must I live? How can I be sure? How can I find out? The clouds parted. The birds resumed their song. I rose to my feet in appreciation.
No amount of wondering suffices to show me what my life will be. There’s only one way to find out. I hope, on my next visit, to play Medtner something wonderful and new. In the meanwhile, I know that my life is far better for his music, that it’s precious, and that it’s mine.