Interruptions and context switching are probably the two most costly things, directly impacting programmer's daily productivity. When there is no way to permanently avoid them, there are some interesting strategies to minimalize their impact.

The Cost of an Interruption

Based on different scientific studies, it takes at least 10-15 minutes to get back into the "zone" after an interruption (Parnin:10, vanSolingen:98). Depending on a task's complexity and your mental energy, definitely it can be more than only 15 minutes:

If an interruption occurs when you have a lot of balls in the air - many pieces of unfinished code that fit together in a complex way - then returning to the flow state is harder. This concept is well known to every programmer, but probably only few heard about The Parable of the Two Watchmakers which perfectly captures all those details in writing, in an understandable form, even for non-programmers:

There once were two watchmakers, named Hora and Tempus, who made very fine watches. The phones in their workshops rang frequently and new customers were constantly calling them. However, Hora prospered while Tempus became poorer and poorer. In the end, Tempus lost his shop. What was the reason behind this?

The watches consisted of about 1000 parts each. The watches that Tempus made were designed such that, when he had to put down a partly assembled watch, it immediately fell into pieces and had to be reassembled from the basic elements. Hora had designed his watches so that he could put together sub-assemblies of about ten components each, and each sub-assembly could be put down without falling apart. Ten of these sub-assemblies could be put together to make a larger sub-assembly, and ten of the larger sub-assemblies constituted the whole watch.

The Cost of Context Switching

When context switching between complex programming tasks, it is usually more mentally challenging to return to the flow, than from a "simple" interruption. To fully switch to something else entirely, you need to flush the cache (short-term memory) and load entire new context. It takes time, and moreover, mental energy, which is finite and it's draining through the day. Those hard limitations are put in place by the human brain.

There is an exceptional book, written by David Rock - Your Brain at Work, which I highly recommend, if you are interested in improving how you spend mental energy through the day. The gist is to treat your brain, during a deep work session, as a stage. When the session is started, you are slowly introducing essential actors (objects, task and pieces of information) into a scene (short-term memory aka cache). To properly light up a scene, you need to use some energy - mental energy.

Mind as a stage during deep work
Mind as a stage, during long deep work sessions

When you get distracted, the entire stage collapses, and it takes some effort to rebuild it from a ground up. But there are some handy techniques to rebuild a stage faster.

Rebuilding The Context

For programmers, rebuilding context after a task switch, usually means returning to an old code which was previously edited or debugged. Before editing starts, programmers navigate to several locations to rebuild context (Parnin:10). But a task resumption can get much more painful, if an IDE doesn't remember a previous working state. That usually means:

  • last opened files,
  • cursor position (line & column) for every opened file
  • debugger breakpoints, variables and expressions
  • bookmarks
  • windows positions with the same layout (including splits)

Rebuilding last working state in IDE manually is usually real pain and mentally draining:

Losing this functionality interrupts my workflow beyond imagination. The opened documents represent a "bookmark" for me and I'm barely able to pick up work again without them.

Every time this happens (...) I am willing to put hours into finding a solution, because the thought of losing my opened document state once more after a work session is terrifying. But this time around (...) nothing of the usual remedies helps (...) This has added another 20 minutes and counting to my two hours put into solving this.

and programmers are perfectly aware of the problem:

This is a much bigger problem than it sounds as you then need to use other ways to remember what you were working on. This causes A LOT of lost time - source.

It’s so frustrating to have to keep pinning the same tabs over & over & over & over & over & over (I think you get the point). (...) My productivity goes down, and my stress level goes up! - source.

Which is way, ability to save working state is a fundamental feature of every good IDE nowadays. But this was not always the case. Vim introduced :mksession command in the v5.2 around 1998:

A Session keeps the Views for all windows, plus the global settings. You can save a Session and when you restore it later the window layout looks the same. You can use a Session to quickly switch between different projects, automatically loading the files you were last working on in that project.

640 x 480 resolution was the standard from 1990 to around 1996. But you could get more screen real estate back then. There is a famous photo of John Carmack working on Quake using a 28-inch 1080p monitor in 1995.

John Carmack and 28-inch 1080p monitor
John Carmack and 28-inch 1080p monitor

Why did he choose 45 kg monitor for about $10k in 1995? For one and the only one reason - more screen real estate. Higher screen real estate = more code visible at once = more dense context. Productivity greatly increases when you have ability to store and access richer context. It is like a larger desk for storing papers when you are studying to exam or doing any tasks that involves using multiple sources of information from the common domain.

I still remember when I was working on my Amiga 1200 using HiRes resolution (640x256) in early 90's, coding in C using CygnusED editor.

CygnusEd on Amiga 2000
CygnusED on Amiga 2000

Only one file at the time, not so much real estate comparing to my main 4K monitor nowadays. From programmer's point of view an impact and the progress in display resolutions on daily productivity is enormous. Let's try to define the observation:

The Law of Context Density

Larger context naturally emerges with higher screen real estate.

The Role of Prospective Memory

Why is so important for programmers to have access to last working context? Let's start with prospective memory definition by John A. Meacham:

Prospective Memory - information with implications for actions to be performed in the future.

Prospective memory is like a sticky note posted on a fridge with reminder to buy a milk after work. Or an important document placed near the exit door, so when you will be leaving the next morning, you won't miss it.

A last working context is a form of prospective memory task, so a resumption failure is a prospective memory failure (Dodhia:05). Did you try to remember shopping list only by memorizing it? It is a nightmare, unless you know how do it properly (e. g. visualization technique). Even short list is hard to remember. We are constantly helping prospective memory by storing bits of information here and there. They act like anchors. When you are entering your (remote) office in the morning, there are visual anchors that will trigger automatically certain areas of prospective memory. Flowers waiting to be watered, a document lying on the desk that need to be processed today etc. Opening an IDE will allow another set of anchors to fire up prospective memory related tasks.

While modern IDEs can be fairly good in remembering last working state, they usually lack ability to switch between them easily. There are few exceptions. Vim has :mksession, Emacs support sessions via different packages. Also, Qt Creator has similar functionality. IntelliJ based IDEs have task and contexts support.

Visual Studio lacks this crucial functionality, which is why I've created an extension called ContextKeeper. It lets you switch between working states, and also automatically switch between them, when changing git branches. Exporting contexts to different machines are fairly easy thanks to relative paths support.

References