This one crazy DevOps language you should learn (during Advent Of Code)

Random bits I learned about an underappreciated language by having fun during Advent Of Code.

This Friday the 2017 edition of Advent Of Code started, a daily treat of small programming puzzles for the holidays. Kudos to Eric Wastl for creating such a fun competition!

Last year I wanted to add a DevOps theme to my participation, so I choose to write solutions in the most important DevOps language. No, not Go. No, also not Python. Definitely not Java. Number one of course is… Bash: present in all Linux systems, almost all Docker containers, heck, even in Windows now. Gluing together systems for almost 30 years.

But would it hold up as a general purpose programming language?

TL;DR: Yes! Almost all puzzles could be solved with short scripts, albeit running a lot slower than other languages. And as a Basher you’re much more badass than those Pythonistas and Rubyists.

Some observations:

Functional programming

I never thought of Bash as a functional programming language, and of course it isn’t in a strict sense: it has (global) variables, subroutines with side effects, etc. But in many puzzles I ended up stitching together common utilities in a functional pipeline, like

cut -b $i < $input | sort | uniq -c | sort -r -n | head -1 | egrep -o ‘.$’

Nice!

Speed

Compared to Go, C, Java or even Python and Ruby, Bash is slow. Like really slow. Main reason: spawning separate subprocesses for command and functional calls ( $(…) style).

Speed tips:

  • Use a Bash builtin command or expression e.g. ${var%:*} rather than $(cut -d: -f1 <<< $var)
  • Use LC_ALL=C to set all string processing to ASCII. This can save up to 20% processing time
  • Use $RETVAL style return values for function calls instead of $(…)
  • Make smart use of all those small commands lurking in /bin, /usr/bin. Did you know ‘rev’ and ‘tac’, to reverse characters and lines?
  • Write a small utility if the regular ones don’t suffice. Eg. md5sum only works on whole files, not lines. A few lines in Go will make your life a lot easier.
  • Use a regex. They may be hard to read, they can be supereffective in parsing and transforming input. E.g. the second puzzle of day 7 could be solved with this one-liner:
grep -Pc ‘([a-z])((?!\1)[a-z])(?=\1)(?=[a-z]*[\[\]](([a-z]*[\[\]]){2})*[a-z]*\2\1\2)’
  • Be smarter! Day 11 featured an interesting problem involving operating elevators to navigate fragile microchips through radiation. It could be solved with an A* search algorithm or even a brute force Breath First Search given your programming language was fast enough and you were willing to spend enough coding time. However some pondering about the essence of the problem reduced it to a simple one liner of multiplications and additions.
  • Use Bash to generate an efficient solving program in a different programming language: The puzzle of day 23 involved interpreting small program coded in a simple assembly language. This program contained so many loops it that interpreting with Bash was prohibitively slow. Solution: write a Bash script that transcodes the assembly to a simple equivalent program in C and compile and run that. Apparently the optimizer in the gcc compiler is so effective that it actually calculated the solution at compile time. So the executable just printed out the right number without computation.

Console graphics

Several puzzles involved navigating a two dimensional maze. The solutions could be calculated without any graphics, but visualizing the algorithm can be insightful (literally) as well as intensely satisfying. Luckily with Bash it’s easy to create LoRes console graphics, with the help of the ‘tput’ command. And with the ‘asciinema’ tool sharing the results is trivial as well. Here is the visualized solution to the puzzle of day 13.

All in all doing the Advent Of Code left me with renewed respect for Bash. It might not be the most complete, or beautiful language or the speediest, but it can do a lot more than just properly starting your Tomcat.

Bash is going to be my weapon of choice in this years Advent of Code again. Happy hacking!

https://github.com/bastiaanb/advent-of-code-2016

https://github.com/bastiaanb/advent-of-code-2017

https://xebia.com/community/advent-of-code