I’ve talked a lot on this blog about writing code that communicates to other developers. Clear names, short functions, responsibilities clearly separated. These things all are intended to lead to code that can be understood quickly by anyone new to the codebase, or even to yourself after you come back to the code months/years later. Clean code is all about writing code for other humans and not for the compiler.

On Friday, Tom Crockett went to twitter to declare:

I think that’s a shame. I feel this is an unfortunate and flawed way of thinking about readable code.

Writing code that’s readable does not in any way imply that the code must therefor be elementary. Writing complex code does not somehow indicate its power level. On the contrary; the more complex the code the greater the need there is to provide an abstraction so that we can more easily reason about it. Only then can we leverage the power of that code to its greatest potential over time. The entire reason we can use the “powerful tools” that Tom mentions in the first place is because their complexity has been abstracted into easy-to-understand tools.

Let’s look at a math analogy. Quick! Solve for x: (I won’t blame you if you skip ahead)

$\frac{ ((2x)^2(x-1)^3(x^3)) }{ (x^3-x^2-4x+4) } = 0$

$\frac{ 1 }{ (x-2) } = 1$

Turns out those 2 equations are exactly the same. The latter is simplified to be easier to understand. Did the simplification some how limit the power of the more complex version? Absurd. It simply made it easier to chew off.

Ok that’s factoring out complexity; what about abstraction?

$(1^x-1) + (2^x-2) + (3^x-3) + (4^x-4) + (5^x-5) + (6^x-6) + (6^x-6) + ... + (n^x-n)$

That’s pretty awful. Can we make an abstraction? Yes.

$\sum_{k=1}^n n^x-n$