Encapsulation isn’t sexy. It’s the chartered accounting of software design. Functional Java programming? Formula freakin’ one. Hybrid cloud computing? Solid booster rockets exploding on a midnight launch-pad. But encapsulation? Do not confuse, however, this lack of oomph with lack of importance. Invaluable invisible support systems surround us. Try living without plumbing for a week. Or electricity. Coupled with its rather sorry PR encapsulation groans under a second burden, that of ambiguity. Every programmer has her or his own definition of what encapsulation is. Most resemble one another, many overlap, but some do little more than reflect randomly-acquired habit.
Yet if we are to discuss the three greatest encapsulation paragraphs we surely need a definition. You may not agree with it but you should at least be in a position to judge the degree to which those paragraphs accord with this definition. How, then, do we solve this ambiguity? It would be nice if there were an international, standard definition of encapsulation upon which to construct our investigation but for this to be the case would require an international organization for standardization, and this international organization for standardization would have had to define, “Encapsulation,” in some meaningful way.
Well – would you believe it? – there actually is such an international organization for standardization. It’s called the, “International Organization for Standardization.” And these good people have officially defined encapsulation (in ISO/IEC 10746-3) as being:
Encapsulation: (drum roll) the property that the information contained in an object is accessible only through interactions at the interfaces supported by the object (cymbal crash!).
(Sound effects added by the author.)
Yes, yes, that’s not your definition. And it begs all sorts of questions. And it defines notions in terms of other, equally-nebulous notions. You are asked, however, not to mindlessly replace your own definition with the above but merely to consider it plausible for this article’s duration. Use it as a tool to crack the shells of the paragraphs to come then toss it aside if you wish. It issues, after all, from the people whose food health-regulations ensured that the breakfast you ate this morning was relatively safe. Let us lend them our ears even if we take them back when they are finished.
Separation of concerns.
You can still catch, “The Godfather: Part II,” in the cinema, Paul Anka croons away at the top of the U.S.A. music charts and the Nevada Desert shrieks as a two-hundred kiloton blast splatters radioactive debris over its vitrifying sands.
Meanwhile in The Netherlands, professor Edsger Dijkstra completes the week by typing another essay. Renowned in computing circles and recipient of the prestigious A. M. Turing award a couple of years earlier, Dijkstra has been writing insightful essays on computing for over a decade, some – such as the infamous Go to statement considered harmful – generating among enthusiasts as much enmity as respect.
Today’s essay is called On the role of scientific thought. It is perhaps a tad wordy, a tad meandering, yet it harbours a core of profound genius. The first of our three greatest paragraphs on encapsulation, the text needs nothing of the context of its surrounding essay to make itself understood:
“Let me try to explain to you, what to my taste is characteristic for all intelligent thinking. It is, that one is willing to study in depth an aspect of one’s subject matter in isolation for the sake of its own consistency, all the time knowing that one is occupying oneself only with one of the aspects. We know that a program must be correct and we can study it from that viewpoint only; we also know that it should be efficient and we can study its efficiency on another day, so to speak. In another mood we may ask ourselves whether, and if so: why, the program is desirable. But nothing is gained âon the contrary!â by tackling these various aspects simultaneously. It is what I sometimes have called “the separation of concerns”, which, even if not perfectly possible, is yet the only available technique for effective ordering of one’s thoughts, that I know of.”
Here, Dijkstra whispers for the first time the phrase, “Separation of concerns,” little knowing that his voice would still reverberate through our digital cloisters almost forty years later.
For who has not heard of the separation of concerns? And who would dream of understanding any non-trivial source code by consuming it in one, mighty brain-gulp rather than slicing it asunder to dissect its individual requirements, its features, its packages or its sub-structures?
Dijkstra was not, however, discussing encapsulation specifically, so how can this be one of the greatest paragraphs on encapsulation? This is an encapsulation piece in that it underwrites encapsulation’s claim that an object’s information is separate from its interfaces. Indeed, encapsulation merely celebrates and exploits this separability without which it would slump de-fanged, a forgotten curiosity.
Today, we think this all obvious. What’s the big deal? Such is the mark of a great idea: it is difficult to conceive of a world in which that idea plays no part. We’ll encounter this plight again.
Two years before Dijkstra clickity-clacked out his masterpiece, Canadian David Parnas had already lit upon a gem of his own. (Our journey declines along an axis of the conceptually abstract rather than the chronological.)
Parnas – like Dijkstra, a university lecturer – published his On the Criteria To Be Used in Decomposing Systems into Modules in December, 1972.
In his paper Parnas describes how to build a software system and concludes with the second of our three greatest paragraphs:
“We have tried to demonstrate by these examples that it is almost always incorrect to begin the decomposition of a system into modules on the basis of a flowchart. We propose instead that one begins with a list of difficult design decisions or design decisions which are likely to change. Each module is then designed to hide such a decision from the others.”
Witness the birth of information-hiding and wonder no more whence Java’s
private modifier comes. If some doubt surrounded the relevance of Dijkstra’s contribution, here is the very essence of encapsulation; for what restricts access to interfaces but that the object’s information is, in some sense, hidden whereas the interfaces are not?
As with separation of concerns, information-hiding seems mundane to us now as steel to the builders of skyscrapers; few rivets clang home to iron-age thoughts. Programming boasts no such longevity, of course, yet forty years of searching has failed to produce information-hiding’s successor.
Our third and final greatest paragraph springs from not one soul but three. In a paper entitled Structured design written for the IBM Systems Journal, W. Stevens, G. Myers and L. Constantine introduced a wealth of extraordinary ideas to the computing universe of 1974. (What was it about the seventies that nurtured such innovation? The flares? The handlebar mustaches? The brownness?)
While separation of concerns and information-hiding provided the foundational mechanisms by which encapsulation is realised, the Structured design paper crystallized the criteria by which the deployment of these mechanisms might be judged. Again, drained of their wonder by repeated use, the words’ over-familiarity belies their significance:
“The fewer and simpler the connections between modules, the easier it is to understand each module without reference to other modules. Minimizing connections between modules also minimises the paths along which changes and errors can propagate into other parts of the system, thus eliminating disastrous, ‘Ripple effects,’ where changes in one part causes errors in another, necessitating additional changes elsewhere, giving rise to new errors, etc.”
The paper dashes on, elaborating these points by introducing the concepts of coupling and cohesion – thereby supplying strong contenders for the fourth and fifth greatest encapsulation paragraphs – but the above exemplifies encapsulation performed well and, more interestingly, badly. When faced with poorly-structured source code, we tend to recoil viscerally from the sight of countless dependencies radiating directionlessly throughout the system. Still today the ripple-effects identified by Messrs Stevens et al. cost our industry hundreds of millions of dollars every year which, given the tools furnished by our three papers here, is odd.
None of the papers presented here enjoyed complete originality even on first publication. Literary shards presaged all. These passages, however, consolidated – and to a huge degree innovated – key principles by which all good software continues to be built today. Their authors deserve recognition as some of computing’s finest minds. Concepts evolve. The world for which software was written in the seventies is not the world now outside our windows. Perhaps some day software will not be composed of individual, interacting parts and so separation of concerns, information-hiding and ripple-effect will fade from the programmer’s vocabulary. That day, however, is not yet come.