DEV Community

Cover image for What is an abstraction?

What is an abstraction?

Eric Normand on July 04, 2017

For a term we use so much in our field, there are very few definitions of abstraction. And when I gave my talk called Building Composable Abstracti...
Collapse
 
kspeakman profile image
Kasey Speakman • Edited

I think one of the biggest reasons abstractions are leaky is because they are too prescriptive. E.g. Inherit from this class. Ok, which methods do I have to override to achieve what I want? Do I need to call base or not? How does this affect other properties of this class? What if the interface is synchronous, but I need to do some async work and it should not be blocking? So the author of this abstraction either has to make all these choices for me up front (sometimes called "opinionated") or has to provide parent class/method permutations for a lot of cases. Or it uses something like Reflection to adapt to many different cases. Either way exposes me to implementation details (as conventions) and limits me down to whatever fits in that box.

The most useful abstractions are ones that expose the operations you can perform and let you opt into and compose only the ones you need. When the abstraction is at the edges of a program (e.g. web server), it should stay as course-grained as possible. A good example of this is the Suave web server. The simplest request handler takes a raw HttpContext and returns one (optionally and asynchronously). You can handle the request absolutely any way you want or ignore it. But Suave has opt-in helpers for common scenarios like GET to handle only HTTP GET requests to a specific URI or setHeader, etc. These helpers are composable, and you can make your own. This abstraction places few limits on me, and I have the option of not learning/using the built-in helpers if I so desire.

Collapse
 
ericnormand profile image
Eric Normand

Hey Kasey,

Yeah, great examples.

We tend to call those things "abstraction". And they are in the Sussman sense since we're naming a compound element. But it's not an abstraction in the Dijkstra sense, because it's not really making it so you can be totally precise. Or at least it's hard to make it precise. You're telling the user of your library that they can subclass this thing but they have to follow all of these poorly-defined rules. To make it less leaky, you should be able to limit the number of rules you have to follow, or at least make them automatically checked.

There are also leaks just from oversights. One of the massive oversights of many languages is allowing a Null Pointer. Now there's this mandatory check after every method returns. Do I actually have the thing the type told me or do I have null? People talk about the cost of Null Pointer exceptions in production. But what about the cost of adding an if statement after every method call? When we design an abstraction, we have to think hard about introducing corner cases and avoid them at all costs.

Rock on!
Eric

Collapse
 
hergin profile image
Huseyin Ergin

I really like Dijkstra's definition (explanation) of abstraction. An abstraction will hide some of the stuff but not all. Only the ones that is related to the target domain of the abstraction should remain. Other irrelevant ones should be hidden. Preliminary examples are domain specific languages. But they are far from perfect at this point.

Collapse
 
ericnormand profile image
Eric Normand

I really like that definition, too.

Follow up question: does your language actually let you do that? I mean, really omit unnecessary details?

Collapse
 
ben profile image
Ben Halpern

Great post, as always, Eric.

I have a thought about this line:

There is a lot of distrust of abstraction in our industry, and I think rightly so.

What about the abstractions that are so helpful and natural that we don't even think of them as examples? Like how we might complain that special effects ruin movies, when the only examples we can think of are the ones that did suck, and the seamless effects go completely unnoticed or unrecalled.

Is it possible that the discourse is skewed a bit too much because it's easier to notice the examples that confirm our distrust?

Collapse
 
ericnormand profile image
Eric Normand

Hey Ben,

Thanks for the kind words.

Abstraction is supremely important in our work. I think we should distrust it more than we do, though, because 1) we don't understand it well and 2) it's too easy to do.

I think your example of special effects is spot on. In the hands of a master, or really good team, you never even notice the abstractions. Our industry is growing so fast that masters are rare. Since it's easy (and fun) to make abstractions willy-nilly, we tend to get lots of bad ones. If we had some process for making good ones, we could learn it and teach it. But right now, we don't really have one.

Really, I'm kind of ashamed. I've been programming since I was 12. I went to college. I have a Master's in Computer Science. And I've never read or written much about abstraction. I've tried to find stuff written on it, and there isn't much. We're unaware of what we're doing.

Rock on!
Eric

Collapse
 
mortoray profile image
edA‑qa mort‑ora‑y

Good article. Abstractions are great, and necessary. But beware the false abstraction antipattern