Focus by Automation

Posted on 2024-03-19

Automation 🤖

I’ve invested leisure time to save time when I’m working hard, not to save keystrokes but to save mental energy for the project at hand.

  • John D. Cook

"DALL-E: A highly focused conveyor belt robot automating daily chores in the style of Pixar animations studios."

In much of the work that I do I try to automate to save mental energy. Automation, to “techy” people, often means to apply some sort of repeatable application of machinery or code in order both free us from manual labor and potentially increase our effective throughput. I’m using a more general interpretation of “automation” when I say “I try to automate to save mental energy” – an interpretation more in line with what John D. Cook points towards in his post quoted and linked to above.

Yes, writing scripts, applying tools and utilities to common everyday programming problems are undeniably “automation”. However, automation in its purest sense isn’t reserved for silicate or metallic machinery only. Biology automates through instinct and practice.

What this means to me in practice is that I relatively often invest a significant amount of time learning new things, practicing various skills, and iterating on my workflows. Not necessarily to save on some imaginary “net sum of time spent”1 – although Randall Munroe of XKCD has shared some thoughts on the topic of – but to ensure I can maintain a certain level of focus in my work when I’m “in the zone”.

Focus 🔍

Why is focus so important? Well, programming is hard and I’m sure also most non-programmers acknowledge the importance of focus when doing work requiring a certain level of immersion.

This little gem from MonkeyUser.com illustrates “focus” for a programmer perfectly:

"https://www.monkeyuser.com/2018/focus/"

I’ve often used the analogy of building a house of cards when explaining to non-programmers how we build mental models of the problems we are solving. Like a house of cards these mental models take considerable time and effort to construct, but topple over and collapse from even the smallest breath of air (interruptions).

Our mental models dissolve faster than cotton candy in water when we’re distracted at an inappropriate time.

How about focus in my work? Sure!

The draft of this post is over a year old. I guess I got distracted!

In fact, I was writing this very post when I realized the prelude was worthy of a post of its own. That became Programming is hard. It gained quite a few views, then I guess I forgot all about this one.

Distractions ⚡

Distractions; the arch enemy of every coder. Distractions break our focus by ripping us out of our flow states. It doesn’t help that programming environments are littered with potential distractions. They come in many shapes and forms, to name a few:

  • ⚡ Physical interruptions from our surroundings (meetings, colleagues, notifications).
  • 🧠 Internal interruptions through impulsive thoughts (spontaneous ideas, procrastination).
  • 🤷 Missing preconditions to perform a task (unclear objectives, yak shaving, tech debt).
  • ➰ Long feedback loops (handovers, difficulty testing, ++).
  • 🥪 An empty stomach.

Some distractions are obvious, others are more subtle.

When we talk about distractions it’s often the “big and obvious” ones that people think of. Those are the distractions where you’re interrupted by someone or something in your surroundings. It may be somebody “just popping over to ask a question” or some meeting looming on the horizon about to evacuate you from your warm and cozy “flow zone”.

In recent years I’ve also grown more conscious of less obvious forms of distractions. Things like small papercuts and annoyances which I previously might have accepted simply as a natural part of “work”. By not acknowledging these minor nuisances as distractions I’ve never stopped to consider how they may negatively affect my productivity or cognitive ability. However, tiny inconveniences can add up to make solving issues more difficult than it needs to be.

Much can be done to reduce the distractions within an organization, but introducing transformational change can be hard for an individual alone. Organizational chaos might even be outside of our control. What we can control to some extent is how we interface with the environment around us.

I find many negative effects of distractions – large and small – can be greatly reduced through personal organization and mastery of your tools.

Organization 📓

I’m personally a big fan of Getting Things Done (GTD), Zettlekasten methods (using emacs with Org Mode and Org-roam), and various other “productivity life-hacks”.

I strongly believe everyone should invest a bit of time and effort into learning a few organizational tools. I don’t have strong opinions on which, but I believe it’s crucial to learn them well enough and integrate them into your daily workflow so that they stay out of your way. It doesn’t even have to be anything digital. A paper notepad is honestly perfectly acceptable too. However, I believe tighter integration into e.g. code editors increases the possibility for distraction free note-taking and organization.

I feel an organizational tool hits the sweetspot when you hardly notice yourself using it.

In my case I’ve achieved such ergonomics using emacs as both my primary code editor and note-taking application. Org mode lets me capture all kinds of fleeting notes and Org-roam complements it by allowing me to quickly refile things into a personal knowledge graph. TODO lists and priorities fit nicely into the same workflow, as does time-tracking.

I must admit I have a lot of issues with emacs, but the way some of these “killer app” plugins integrate into a comprehensive productivity tool I have yet to find anything matching what I’m after.

There is A LOT of literature on personal organization, so I don’t want to spend too much time on this topic in this post. Let’s move on to another critical tool in the battle against distractions: mastery.

The value of mastery 🧙

I briefly touched on “practice makes perfect” in produce, don’t consume and how practice can be incorporated into constructive efforts. Writing this post I’ve also come to realize that another trait of practice and mastery is how automating our skill through practice helps us cancel out distractions in order to maintain focus.

Mastering our tools is important as it allows our brains to focus on the task at hand. If we are forced to spend a significant amount of our brain power learning programming language syntax, editor bindings or APIs then we have less mental energy to spend on solving actual problems. Battling complexity on multiple fronts increases cognitive load and often a loss of focus.

A dancer who doesn’t know the basic moves of a dance style will have great trouble connecting motions in the choreography while maintaining rhythm and composure. Similarly, a programmer who constantly stumble on basic syntax or interpreting compiler errors will have a harder time constructing a mental model of the problem she’s solving.

But we do not necessary have to become specialists to become effective. In fact, becoming and staying a proper expert in more than a handful of fields is a fools errand in modern software development. Ecosystems evolve too quickly, new tools and practices come and go. Not to mention the looming paradigm shift of artificial intelligence and how it might render significant aspects of conventional programming obsolete2.

What I find useful is to learn enough about a wide variety of topics to build a basic intuition for when specific technologies or methodologies will help solve the problems we’re faced with. You’ll then eventually start picking out what matters to you and your expertise will grow somewhat organically3. Also try to surround yourself with smart people complementing your own abilities.

Practice and repetition is crucial to become a master in just about anything. A musician spends time with her instrument to improve, programmers spend time with their “tech stacks”, editors and tools. It’s a matter of starting somewhere. Experts weren’t born experts. And even though talent or determination allow some to progress faster than others nobody who achieve mastery within any discipline will admit to not having worked hard – or for a long time – to acquire the skill they possess.

Just as a musician is likely to butcher an unfamiliar instrument, a programmer dropped into a new development environment will most definitely experience some initial regression in their productivity. This is normal, but it is also the way we learn. The difficulty is knowing (or choosing) what to learn, and when. In the middle of a high-stakes project is probably not the right time to pick up a new language or framework4.

Whether you consider yourself a specialist or a generalist I believe software development is quite unique in the way many skills are transferable across environments. Some skills invested transcend their technologies almost entirely due to their pervasiveness or general applicability.

Typing speed

Muscle memory and habits are both important abilities of the body and mind to increase our efficiency and reduce our cognitive load. Making things more automatic allows us to complete repeatable tasks faster or do so without sacrificing our ability to reason about the problems we’re currently solving.

Most seasoned programmers know that we spend significantly more time reading and navigation through code than actually changing existing code or writing new code. For this reason it’s easy to assume that learning effective typing is secondary to learning how to structure programs really well. I don’t disagree, yet I have the impression that many of the really amazing programmers I know are also great typists.

I believe there might be a very simple reason for this correlation – besides the obvious take that great programmers spend a lot of time in front of their computer, thus become great typists. No, I believe by being able to generate many programs fast you are also able to attempt many possible solutions faster. Difficult problems require thinking, I know. But few things beat the speed of finding code problems as actually passing code through a compiler or an interpreter and executing it.

I would say it’s worth putting effort into improving your typing. Not with the end-goal “writing as fast as possible” in mind of, but rather to interface as efficiently as possible with the computer. Why then not also try to improve how you type? Let’s take vi/vim and modal editing as an example.

Vim bindings

In (neo)vim there are keybindings bound to operations which operate on various textual structures.

Bindings may operate on “bodies” of text like letters, words, sentences or paragraphs. Or they operate on pairs of quotes, parentheses and brackets. They can work on locations like the beginning and end of a buffer. Or even metadata not represented in the buffer itself, like the location of compilation errors from an external tool or spelling errors from a spell checker.

Once vim motions are internalized it’s amazing how efficient it feels to “delete all word” (daw) or “change in paragraph” (cip) without breaking a sweat. The great strength and power of vim motion bindings come from how a few handfuls of general-purpose operations translate across different types of textual motions, from prose to any style of programming and markup languages.

Editors like Kakoune and Helix attempt to improve further on this concept. I have little experience using them, but I struggle to see how investing significant time into them at this point is worth the effort. After all, one of the main benefits of vim and vim motions is how pervasive they are.

There are many ways people can argue that learning vim-style modal editing helps their productivity. It can, however, be somewhat tricky to determine what exactly people benefit from it. Personally I’m certain the time I invested into learning motion bindings and compound operations many years ago has reaped dividends way past the initial investment.

Optimize the common paths

But how? By letting me type faster? What has typing and vim motions to do with avoiding distractions?

Everything!

The keyboard is still my main interface to the computer. As long as it continues to be it matters to me to wield it well.

Similarly to vim motions most mainstream $SHELL prompts default to emacs-style readline bindings5. To me that was motivation enough to put some effort into internalize the most common readline keyboard bindings on the CLI (for emacs users this is trivial).

Raise your hand if you know how to undo edit operations in readline ✋ (yes, C-/ and C-u C-/ works in your prompt!)

Programming is littered with micro-distractions, remember? Not only do you increase your efficiency at typing out actual programs by learning effective text navigation and manipulation (as well as text generation through snippets and generative A.I.). You also do so while sparing your brain from having to think about these trivial “problems” and road-blocks.

This is just as true in your editor as outside of it.

It’s not uncommon to find myself thinking about my next steps while doing some other thing like text navigation or manipulation using either vim or readline keybindings. By now they’re so ingrained in muscle memory that I more often that not think about what I need to do, not how. It just happens.

And let me say that the point of this section is not to boast or rave about vim and emacs bindings. The point is that by learning your tools really well they eventually get out of your way and you’re free to tackle the actual problems you’re faced with. It’s even better if these skills are applicable in a wide variety of applications and environments – try to stick to defaults.

Braaains 🧠

I don’t mind learning, but I want to choose – within my power – when, how and how much to learn. After all, learning is all about rewiring our brains. It’s mental exercise, and like physical exercise learning can be very exhausting. The same goes for problem solving – it’s our brains applying our existing knowledge in order to achieve something new.

Knowing when to invest time into learning, automation or optimization is not trivial. Done prematurely there’s the risk of sinking costs into efforts that won’t pay off, yet stubbornly sticking to old ways could be impeding future efficiency. A big part of maturing as a software developer is knowing (or more likely, sensing) when the time is right for you.

The biggest bottleneck of software development is still the (human) brain. It’s a precious resource, but it can only do so much and distractions greatly reduce its capacity.

Through practice and mastery, by building and honing physical and internal tools, we can offload our brains to focus much more of its effort on the problems we’re solving. By allocating more brainpower into solving problems we’re also more likely to succeed in solving some of the hard ones, and to more gracefully recover from distractions when they occur.

Now, what was I doing again…?

Footnotes


  1. Although measuring this would’ve been a very fun experiment had we had access to parallel universes.↩︎

  2. Nah, don’t worry. You’ll be fine!↩︎

  3. Don’t get me wrong. I find it very important to combine theoretical studying with practice and applying knowledge.↩︎

  4. Or who knows, maybe it is.↩︎

  5. Many shells also support vi mode bindings, but it’s rarely the default.↩︎