The Metaphors We Build By
The practice of software development is frequently described in terms of metaphors. The point being to establish a non-obvious connection or analogy between the creation of abstract logical structures executed by computers and other pursuits that are somehow similar. Metaphors are powerful cognitive constructs by which two words or ideas are linked by association or identity even if they seem dissimilar.
When Shakespeare said “all the world’s a stage”, he was using metaphor. A connection is made between dissimilar things, our experience of life (in all it’s complexity) is equated with a stage play. Humans are characters in a drama and we play our various roles. Metaphors work because they allow our mind to look at the objects in question from a different perspective.
Metaphors abound when it comes to computers. Recycle bins where deleted files go are in no way ‘green’. Files themselves aren’t actual files like you would find in a filing cabinet and the directory tree that you find those computer files in do not germinate from seeds and grow in forests. Word processors have widows even though they never had a spouse. Processes can be orphans or zombies, even though none have ever appeared in a Dickens novel or been killed by a man named Ash sporting a chainsaw for a hand. The cloud isn’t some magical computing resource in the sky, it’s someone else’s computers in a data center you can’t physically access. These metaphors have been in place for so long that we operate with the metaphors as models until something interferes with the connection.
Using metaphors in this fashion shows just how much we connect abstractions and how these connections can act as point of reference or a way of working with complex subjects. Extreme Programming recognizes the power of metaphor by advocating a System Metaphor that can actually aid in the design of software and answer questions about implementation during development. This can be powerful, if such a metaphor can be found.
As with all mental models, metaphors do break down at some point. If we’re using them as points of reference or filtering thought processes through them we need to recognize the limitations. This applies even to the metaphors we use for the creation of software.
Viewing development as software ‘construction’ is one such metaphor that is very compelling and effective. So compelling and effective that it has been the most enduring metaphor for development. Steve McConnell strongly supports this metaphor in his book Code Complete. Scaffolding, tools, design, plumbing, foundation, all these terms have meaning in both construction and development (astute readers may also note that architects and those implementing the designs may have disagreements in both fields as well). These same conceptual alignments occur when you use the term ‘software engineering’ (also a metaphor). While these metaphors are powerful, they ignore a couple of important points.
Software is not the same kind of thing as a building. Buildings cannot be easily changed except in superficial ways, but there is the perception that software is highly malleable. Similarly, software isn’t a physical entity. It is an abstract and highly complex logical structure. The conceptual effort required for complex software is higher than that required for construction (note, this is complete conjecture and, as a programmer, I am biased). The majority of the cost of a building is the materials and labor required to put it together. The design is expensive, but it is orders of magnitude cheaper than construction. The process of making a piece of software is different. Most of the expense is in the design (because the code is the design). Construction in terms of compiling and turning code into a running application are effectively free. We can throw away the finished product and rebuild it after making significant changes. To date, buildings and other physical objects cannot do this.
With the rise of agile development, a new metaphor has increased in popularity. Software is ‘grown’ and development is a more organic process. Given the iterative nature of Agile practices, this metaphor is appropriate. Working software starts small and grows in size, functionality and aesthetics as a project progresses. While it is an effective metaphor for how development is done, the extent to which it can be leveraged is limited. We don’t ‘weed’ code bases, ‘harvest’ unit tests or ‘trim’, ‘prune’ or ‘plant’ much of anything.
Another popular metaphor identifies the creation of software as a ‘craft’. Historically, craftsmanship has been viewed as a creative endeavor that blends utility and art in the hands of a skilled practitioner. The term implies a level of quality and value that is difficult to find in a world of mass production, assembly lines and throw-away goods. Craftsmanship brings to mind the use of good tools, a certain amount of artistry, and pride in the finished work. It also carries with it the idea of cyclical mentoring – the master helps the apprentice become a journeyman who will one day become a master that will take on an apprentice, and so on. Good associations, but there are some downsides. It is possible to overvalue quality. Or at least to overvalue it in relation to the problem domain (it’s probably okay if an app crashes but pacemaker software had better be rock solid). It’s easy for software craftspeople to let perfect be the enemy of the good.
As a brief digression, I admit that I really want to like this metaphor. Unfortunately, the words ’software craftsmanship’ seem to get in their own way. The word ‘craftsman’ can come across as pretentious. And any title ending in the word ‘man’ is in obvious need rework these days. As we saw a few sentences back, ‘craftspeople’ doesn’t exactly roll off the tongue. Artisan might have been a useful alternative until the term ‘artisanal’ became so grossly overused. Seems an uphill marketing battle.
One of the oldest metaphors for writing software is that it is, well, writing. In a way, this evokes of images of a developer sitting down at a desk with a pen or pencil in hand to turn out code in calligraphic strokes on heavy bond paper. While that image isn’t entirely accurate, it does have its uses. While in college, I frequently wrote functions or entire source files on paper when I didn’t have access to a computer. This forced me to think through the logic more than I would with a keyboard in front of me. While it was a slower process, I frequently found that the code I wrote on paper first was less prone to have errors because of the mental walkthroughs I had to do. Obviously, this is not the most efficient way to create software. One thing the writing metaphor does promote is code readability. It also carries notions of programming style and an emphasis on originality. This metaphor is likely the reason that the individual writing a piece of software is called the ‘author’ rather than the ‘developer’ or the ‘programmer’.
This is not a widespread metaphor. It may also not be a useful one. I admit, it is included here only because I once used it, but I think that says more about me than it does anything else. Storytelling is itself a craft, one of the oldest there is since it has been a part of human culture since the very beginning. It is a craft that takes place primarily in the mind and imagination of the writer, the telling or writing is simply a storage or transfer mechanism. It does overlap with the writing metaphor, but storytelling is very different from just writing. Good stories are built over time. They start with an idea and are gradually built into coherent and connected structures that depend on each other to work. Parts may be changed or rewritten if they don’t work well enough with the rest of the story. Stories and their components should be beautifully written or told. Many stories use common character types or devices (archetypes) that are very similar to Patterns. Good stories give something to the people to whom the story is being told. They provide entertainment, new ideas, or new ways of looking at the world. Good stories are powerful works of art that have the potential to change the way people think and operate.
Which Metaphor Do I Use
At present, I find that the writing metaphor is still the most applicable. Programming and writing are both about constructing coherent, semi-ephemeral structures for a purpose. Both involve editing, and rewriting. Both have vast subcategories that accomplish very different ends - just as writing a tweet is different from writing a brochure which is different from writing a novel, so writing a script is different from writing operating system is different from writing a mobile app. On both sides you have different sorts of results with different conventions, expectations, tools, etc. It starts to become less applicable when you start having teams of people collaborating. Or when you recall that writing is for communicating with humans while programming is for communicating with both computers and with other programmers (if you are doing it correctly).
There Is No Metaphor
Many other metaphors have been used for software development – it is science, art, herding cats, nailing jello to a tree, a bazaar, a cathedral, slaying werewolves, a process, and a factory. Correlations between the ideas can be seen with all the metaphors I’ve mentioned, but the depth to which that correlation can be pushed is variable. Taking any metaphor ‘too far’ has negative value. Similarities may exist but we must remember that they are fundamentally different types of things.
Which brings us to the crux of the matter - the creation of software is precisely equal to nothing except itself. When we misunderstand this and confuse the metaphor with reality we will get results that we don’t want. This is part of why project management can be such a challenge with software. You think you are operating in one realm (construction, for example) and you plan out phases and allocate resources and draft designs and then you have something like the waterfall model of software where things look good for a while and then the wheels come off and the project ends up late, over budget and doesn’t solve the actual need. This happens when your fundamental understanding is flawed. This is what author Neal Stephenson calls ‘metaphor shear’, the realization “that you’ve been living and thinking inside a metaphor that is essentially bogus.”
Computer pioneer Edsger Dijkstra pointed out that programmers have to work with nine orders of magnitude between the lowest level of detail and the highest. One mechanism to cope with this level of complexity is to view the software creation process as a metaphor and identify the correspondence between two ideas. Metaphors are mental models and those mental models are useful tools. As with all tools, they are useful so long as they are used properly, provide value and don’t break. Ill-chosen metaphors, metaphors that are extended past their limit of utility, or those that are of very limited applicability are like choosing the wrong tool to accomplish a task. The point is to find the right metaphor for the job.