Compound complexity

I’ve started to read through Michael Fogus’ list of recommended technical papers and ran across this gem from Out of the Tar Pit:

Complexity breeds complexity. There are a whole set of secondary causes of complexity. This covers all complexity introduced as a result of not being able to clearly understand a system. Duplication is a prime example of this — if (due to state, control or code volume) it is not clear that functionality already exists, or it is too complex to understand whether what exists does exactly what is required, there will be a strong tendency to duplicate. This is particularly true in the presence of time pressures.

Within a few hours of reading that quote I had a conversation illustrating it. I talked with someone who needed to make a small change to a complex section of code. He said the code had three minor variations on the same chunk of functionality. He could get his job done much faster in the short term if he simply added a forth mutation to the code base. He refused to do that, but many developers would not refuse.

Suppose the rate of growth in complexity of a project is proportional to how complex the project is. And suppose, as the quote above suggests, that the proportionality constant is the time pressure. Then the complexity over time is given by

y‘(t) = a y(t)

where y(t) is complexity at time t and a is the time pressure. Then complexity grows exponentially. The solution to the equation is

y(t) = y0 eat

where y0 is the initial complexity. This isn’t meant to be an exact model, just a back-of-the-envelope illustration. On the other hand, I’ve seen situations where it gives a fairly good description of a project for a while. Complexity can grow exponentially like compound interest, and the greater the pressure, the greater the rate of compounding.

Now suppose there’s a different kind of time pressure, a pressure to simplify a project. This would correspond to a negative value of the proportionality constant a. If there were such pressure, this would mean that complexity would decrease exponentially.

I don’t think this kind of negative pressure on complexity is as realistic as positive pressure, but it’s not entirely unrealistic either. In the rare case of pressure to simplify, removing one source of complexity could lead to cascading effects. Because we don’t need this one thing any more, we don’t need these other things that were only there to prop it up, etc. There could be a sustained decrease in complexity, though it probably would not be exponential.

Related post: A little simplification goes a long way

5 thoughts on “Compound complexity

  1. Several times I’ve run into situations where I’ve had to write code to deal with complex/changing situations. Where I could, I’ve made my code rule based (or created a domain specific language). The application is more complicated (sometimes, much more so), but it’s also much more stable, because the changes I have to make are in external files/tables. (In one case, I was even able to give users tools to do common changes.)
    Many times you’re stuck with having to implement a complex solution to a complex problem. How you implement that complexity can make a big difference in how easy your code is to maintain.

  2. The issue of copy/pasting code has more to do with the economics of software development than with the complexity of code. When there is a big downside risk of breaking running code (particularly when there is no automated test suite to act as a safety net), the natural tendency for a developer is to copy/modify/add rather then change what is already there even if the existing code is trivial. Having complex code without doubt increases the risk of breaking something, but you need the fear of adverse consequences to prevent action. As a generalization, the longer a system lives and the larger it becomes then the more people will depend upon it and the greater the risk of breaking it.

  3. This negative complexity pressure is called refactoring
    http://en.wikipedia.org/wiki/Refactoring
    It’s a part of any “normal” development process. Not refactored usually – technical demos , project dropped in the middle and project “scams” – project started without intention to be finished. Reviving dormant project usually started with refactoring.

Comments are closed.