Ye Cannae Change the Laws of Physics • Kevlin Henney • GOTO 2025
Kevlin Henney explores the limits of software abstraction, arguing that while software is an 'executable fiction,' it is ultimately constrained by the fundamental laws of physics. This talk deconstructs common metaphors like 'velocity' and 'roadmap' and delves into the real-world implications of physical constants like the speed of light and impossibility theorems like CAP.
Software development is the practice of creating “executable fictions.” We build worlds with their own rules, relying on abstractions that allow us to suspend our disbelief. However, these fictions are ultimately executed on physical hardware within a physical universe, and we cannot ignore its fundamental laws. This exploration delves into the metaphors we borrow from physics, the constraints physics imposes on our systems, and how a deeper understanding of these limits can improve our designs.
Abstraction, Infinity, and Physical Work
A purely functional Haskell solution to the FizzBuzz problem can be elegantly constructed using five infinite lists, demonstrating the power of mathematical abstraction. However, this highlights a critical divide: nature does not do infinities. In the real world, infinities are a mathematical construct. When a physicist refers to a “singularity of infinite density,” it’s a polite way of saying their model is broken at that point. The universe is distinctly physical and bounded.
This relates to the concept of “side effects” in functional programming. A computation with zero side effects is a computer that is turned off. Every computation is a physical process that consumes electricity and performs work, which is measured in joules or kilowatt-hours. This physical reality is a side effect that we often abstract away, but it never truly disappears.
Metaphors We Compute By
We frequently use metaphors to reason about software, but we must choose them carefully and understand their implications.
-
Entropy vs. Technical Debt: Manny Lehman observed in 1980 that as a program evolves, its complexity increases unless work is done to maintain or reduce it. This is a law of software entropy. Even well-executed changes disturb the system’s equilibrium, creating a mess that requires cleanup. While “technical debt” is a common metaphor, a more fitting one might be “housework,” as proposed by Ivon Lamb. It’s the constant, necessary work you have to do simply by virtue of “living” in the system.
-
Velocity vs. Speed: Many agile teams claim to measure “velocity,” but they are actually measuring speed. Velocity is a vector—it has both magnitude and direction. A team can have high speed but be heading in completely the wrong direction, making negative progress. True velocity accounts for whether you are building the right thing in the right way.
-
Roadmaps: The common project “roadmap” is often just a single, linear path. This misses the entire point of a map. A real roadmap shows a network of roads, offering choices, alternative routes, and the ability to adapt to changing conditions. A single-track plan is not a map; it’s a railroad.
The Tyranny of Time and Space
Our intuitive understanding of time and the future often fails us when building complex systems.
-
The Unknowable Future: The desire to “future-proof” systems is often futile because, as Yoda said, “impossible to see, the future is.” We can’t truly prioritize by “business value” because that value will only be known in the future. At best, we can prioritize by “business value estimate,” which correctly frames it as an uncertain prediction with error bars, not a hard number.
-
The Speed of Causality: The speed of light, C, is not just a suggestion; it’s a hard limit. The distance from London to New York is about 19 light-milliseconds. A requirement for data to be synchronized between these two locations in under 10 milliseconds is therefore physically impossible. C is not just the speed of light; it is the speed of causality—the maximum speed at which one event can affect another.
-
Ordering in Distributed Systems: As Leslie Lamport detailed in his 1978 paper, “Time, Clocks, and the Ordering of Events in a Distributed System,” it is sometimes impossible to say that one of two events occurred first. The “happened before” relation is only a partial ordering. This is a fundamental consequence of the finite speed of causality. We are so accustomed to a totally ordered sequence of events that the asynchronicity inherent in distributed systems messes with our perception of time.
Consequences for System Design
These physical and logical limits have direct consequences for how we design and build software.
-
State Management and the “Oh Moment”: A common UI bug is the “oh moment,” where an application first displays “You have no items” before loading and displaying the user’s actual data. This is a state management failure. The system confuses the initial state of its internal collection (empty) with the user’s true state. The correct model involves distinct states:
loadinganddisplayable. During theloadingstate, the UI should indicate that it is fetching data, not present false information. -
The CAP Theorem: Brewer’s Conjecture, now the CAP theorem, is an impossibility theorem for distributed systems. It states that a system can only provide two out of three guarantees: Consistency, Availability, and Partition Tolerance. This is a fundamental trade-off, much like Heisenberg’s Uncertainty Principle. It provides, as Douglas Adams wrote, a “rigidly defined area of doubt and uncertainty.” You cannot beat the CAP theorem; you can only choose which trade-offs to make.
-
Eventual Consistency vs. Bugs: While eventual consistency is a feature of many distributed systems, it is not an excuse for a client application to contradict itself. If a UI displays a header saying “You have 2 things” but the list below shows 3 items, that is not eventual consistency—it is a bug. The client has a responsibility to integrate potentially inconsistent data and present a coherent view to the user, not to gaslight them.
Ultimately, as Aldous Huxley observed, “reality cannot be ignored except at a price.” While our abstractions are powerful and necessary, we must respect the fundamental limits of the universe in which our code runs.