I might be terrible at learning human languages, but I really enjoy learning programming languages. In my last post, I mentioned setting up Johnny.Decimal, and that I was thinking of writing some tools to help me interact with the system. I’m a dedicated Alfred user, and when I spotted a very nifty library called awgo for writing Alfred workflows in Go, it seemed like the perfect excuse to dip my toes in Go and learn another programming language. The result after only a couple of weeks of tinkering in spare moments was this alfred-jd workflow. I really like Go.
After only two weeks, I am obviously nowhere near an expert (or even a novice), but Go is a language that is easy to pick up. You can get started quickly and write some surprisingly useful and elegant code without needing to spend months learning a lot of syntax. The awgo library helped me enormously, as the wrappers it provides (not to mention the very useful examples given), did a lot of the heavy lifting and enabled me to have something basically functional running quite quickly.
But Go itself is a very programmer-friendly language. The syntax is relatively simple but powerful, and if you run through the interactive Go Tour, you’ll learn most of what you need. It is a compiled language, and if you use (as I do) an editor with support for the Go LSP server (Emacs in my case), it’s like having a Go expert looking over your shoulder and pointing out what you are doing wrong. It interactively picks up on unused variables, incorrect types and so on, and automatically formats your code each time you save. If you pay attention to these errors and learn how to fix them, your code will usually build first time, and you quickly get into good habits.
I am finding Go to be an elegant and efficient language. The standard libraries that are built into Go are comprehensive and easy to use, and almost everything you need (from a compiler to a test framework and full offline documentation of the standard libraries) is built in when you install Go. If you’ve written code in languages like Python or Ruby (which are themselves fun to code in), the fact that you don’t need to install virtual environments to manage packages and their dependencies is a real relief. My only previous exposure to Go was as an end-user of Hugo (the software that builds this blog). Even then I had benefited from the fact that Go builds binaries (cross-platform if you want) which are self-contained: all you need to do is install the single binary, and everything will work. That, coupled with the fact that Go is so fast and efficient, and has good built-in libraries for command line flags and so on, makes me think that I will probably build little scripts to solve tasks in Go from now on. Ruby or Python always seem like the best use-case for those kinds of tasks, but then you try running your script again six months after writing it, and find that it doesn’t work because some dependency has broken somewhere.
I usually find that when I learn programming languages, the basics are easy to pick up, but then I hit a wall when trying to build larger, more modular programmes into libraries. However, I quite quickly picked up the way that Go packages work, because it’s very straightforward. Similarly, understanding how to use libraries (standard or external) is easy to grasp. I’m planning to improve and extend my Alfred workflow, but I’m now reading a couple of Go books (Go in Action and Powerful Command-Line Applications in Go) in order to deepen my knowledge and make sure that I am building things in an idiomatically ‘Go’ way that makes the most of the language and is robust. So far, I’ve actually grasped how pointers work, which is something which had eluded me whenever I had come across them in other languages, so that is definite progress!