Sunday Selection 2012-07-01

Around the Web

Hackers and Fighters

When it comes to the debate between computer science and programming I’m of the opinion that knowing some computer science will make you a better programmer. Being a regular programmer will give you a better appreciation of the problems scientists need to solve. I’d love to see a proper scientific test of this hypothesis rather the jumble of anecdote and posturing that exists on the web today. This article is one of the more balanced ones and gives a worthwhile metaphorical veiw of the matter.

How One Hacker Quit the Programming Life for Bluer Skies

As much as I love writing code for my day job and wouldn’t be doing anything else, I don’t think that need be true for everyone. For a lot of programmers, writing code is just a day job and that’s ok. I find the notion that “real programmers” program day-in-day-night to be rather silly. You should do what makes you happy. Peer pressure that makes you produce more is still peer pressure. How good you are as programmer is determined by the quality of your code – not the hours you put in and not the number of open-source projects you maintain. And when you decide that you’ve had enough, don’t be afraid to go do something more interesting.

A much higher education

These are interesting times for academia and education in general. While I’m all for free (both as in beer and in freedom) digital distribution and decentralized, on-demand self-education, you can pry my expensive liberal arts education from my cold dead hands. I don’t think the higher-education system is unsustainable, I think there’s increasing pressure to commercialize and corporatize it and we’re unwilling to explore other options. Education is the foundation of a free society. Academic freedom is one of the pillars of modern science and technology. It’s about time we took that seriously.

Video

Jon Moore on Hypermedia APIs

Programming for the web is still one of my blind spots. That being said, I find the idea of programmatic exploration of APIs very interesting. I don’t fully understand all the implications and applications and I don’t think I will until I write a hypermedia application. But if you’re interested in knowing what programming for the modern web is like, I think this is a good start.

My Emacs Config

I’ve released parts of my emacs configuration on Github. Fork away! I first started really getting into Emacs after reading Steve Yegge’s blog posts on the matter. Since then I’ve pretty much fallen in love with Emacs, waxed eloquently (or maybe not so eloquently) about why it’s a power tool and despite all the cool modern editors and IDEs you can pry my Emacs from my cold dead hands.

I add to my Emacs configuration every time I embark on a project in a new language or using a new toolset. Currently I have a good 15MB worth of Elisp code for programming in C, Python, JavaScript and Ruby, dealing with XML and Git, blogging with WordPress etc. etc. All that stuff is not in the repository (though the names of some of the packages are if you want them). What is on Github are my general Emacs configurations, custom keybindings and custom Elisp functions for moving around the buffer and relocating files.

A note on keybindings

Most of my keybindings are different from the standard Emacs ones. I rebound them to be easier for me to remember, especially the movement keybindings. The mnenomic I use is:

  • `f` key moves forward
  • `b` key moves backward
  • `d` key kills (deletes) forwards
  • `w` key kills (deletes) backwards

I use the Ctrl and Alt modifiers to make these actions work on words or individual letters. The Ctrl key makes each of the above operate by word and the Alt or Meta modifier makes them work by letter. The Ctrl-m combination is a prefix key for various functions to reposition the current open buffer in the window. The functions are defined in `functions.el`.

A note on tools

I’m a great believer in customizing and shaping your tools to fit your work and your workflow. However, I believe more strongly that the code is not the point and that your tools are definitely not the point. In keeping with that I rarely tinker with my Emacs setup nowadays: I’ve found a configuration that works for me and is acceptably efficient. If I move to new tools and language (Haskell and Go are on the horizon) then I might make more additions.

The Code is Not the Point

There’s this meme in the programming community of thinking of our code as art. This is not a new phenomenon – it dates back at least to The Art of Computer Programming in 1968. More recently we have Paul Graham to thank for drawing the comparison between Hackers and Painters. With the rise of languages like Ruby and Processing and personalities like _why the lucky stiff programming has been gaining a reputation as an art form and a source of creative joy. And it should be. I love programming, it makes me feel good and I feel much better on days I’ve written code and produced something than on days I haven’t. However, I think the “code is art” or “programmers are artists” meme can be misleading because the code is not the point.

Miyamoto Musashi was a medieval Japanese swordsman and Ronin, widely regarded as the best swordsman of all time. He was also the author of a book titled “The Book of Five Rings” – a book on swordsmanship, strategy, tactics and philosophy that is still relevant today. There is one passage in the book that is relevant to our discussion:

The primary thing when you take a sword in your hands is your intention to cut the enemy, whatever the means. Whenever you parry, hit, spring, strike or touch the enemy’s cutting sword, you must cut the enemy in the same movement. It is essential to attain this. If you think only of hitting, springing, striking or touching the enemy, you will not be able actually to cut him.

The primary thing when you take an editor in your hands is your intention to solve the problem, whatever the means. Whether you write a script, a unit test, a function, or a library, you must move towards the solution in the same movement. It is essential to attain this. If you think only of scripts, tests, functions or libraries, you will not be able to actually solve the problem.

Because the code and it’s surrounding artifacts, including your sense of beauty, is not the point. It does not matter how much code you’ve written, what your test coverage is, how much you’ve learned in the process, if you haven’t not solved the problem (or solved it inadequately, or solved the wrong problem). Anything that does not bring you closer to your solution is suspect.

Does this mean that clean code, good comments, test coverage are not necessary or important? Of course not. If your code is not well-written and clear, are you sure you’ve solved the problem? If you have no tests, are you sure you’ve solved all aspects of the problem? If you have no documentation, how will others use and improve on your solution?

Does this mean that your code is not art? Does this you mean you should not carry an artists’ sense of elegance and aesthetics? Of course not. By all means take pride in your work. Make it a point of honor that others can understand your code without sending a dozen emails. Please aim for the solution that is not just correct, but also elegant, concise and efficient.

But keep in mind that the code is not the point. Beauty, elegance and pride are no substitutes for correctness. We are scientists and engineers first, artists second. If the theory does not fit the facts, if the code does not solve the problem, it must be discarded no matter how beautiful it is.

I don’t think of myself as an artist any more. My code is not art. I take pride in my work but it is the pride of an engineer. I want my code to have more in common with a Rolls Royce engine than it does with Sunflowers. I try to do the cleanest, most elegant job I can. But whenever I write code, the intention is to cut the enemy, whatever the means.

Python as a glue language

I’ve spent the better part of the past few weeks redoing much of the architecture for my main research project. As part of a programming languages research group I also have frequent discussions on the relative merits of various languages. Personally I’ve always liked Python and used it extensively for both professional and personal projects. I’ve used Python for both standalone programs and for tying other programs together. My roommate likes Bash for his scripting needs but I think Python is a better glue language.

My scripting days started with Perl about 6 years ago but I quickly gave up Perl in favor of Python. I don’t entirely remember why, but I do remember getting the distinct impression that Python was much cleaner (and all-round nicer) than Perl. Python has a lot of things going for it as a scripting language – a large “batteries included” standard library, lots of handy string functions for data mangling and great interfaces to the underlying OS.

Python also has decent features for being a general purpose language. It has a good implementation of object-orientation and classes (though the bolts are showing), first class functions, an acceptable module system and a clean, if somewhat straitjacketed syntax. There’s a thriving ecosystem with a centralized repository and a wide variety of libraries. I wish there were optional static types and declarative data types, but I guess you can’t have everything in life.

Where Python shines is at the intersection of quick scripting and full-fledged applications. I’ve found that it’s delightfully easy to go from a bunch of scripts lashed together to a more cohesive application or framework.

As an example I moved my research infrastructure from a bunch of Python and shell scripts to a framework for interacting with virtual machines and virtual networks. We’re using a network virtualizer called Mininet which is built in Python. Mininet is a well engineered piece of research infrastructure with a clean and Pythonic interface as well as understandable internals. Previously I would start by writing a Python script to instantiate a Mininet virtual network. Then I would run a bunch of scripts by hand to start up virtual machines connected to said network. These scripts would use the standard Linux tools to configure virtual network devices and start Qemu virtual machines. There were three different scripts each of which took a bunch of different parameters. Getting a full setup going involved a good amount of jumping around terminals and typing commands in the right order. Not very tedious, but enough to get annoying after a while. And besides I wouldn’t be much of a programmer if I wasn’t automating as much as possible.

So I went about unifying all this scripting into a single Python framework. I subclassed some of the Mininet classes so that I could get rid of boilerplate involved in setting up a network. I wrapped the shell scripts in a thin layer of Python so I could run them programmatically. I could have replaced the shell scripts with Python equivalents directly but there was no pressing need to do that. Finally I used Python’s dictionaries to configure the VMs declaratively. While I would have liked algebraic data types and a strong type system, I hand-rolled a verifier without much difficulty. OCaml and Haskell have definitely spoiled me.

How is this beneficial? Besides just the pure automation we now have a programmable, object-oriented interface to our deployment setup. The whole shebang – networks, VMs and test programs – can be set up and run from a single Python script. Since I extended Mininet and followed its conventions anyone familiar with Mininet can get started using our setup quickly. Instead of having configurations floating around in different Python files and shell scripts it’s in one place making it easy to change and remain consistent. By layering over and isolating the command-line interface to Qemu we can potentially move to other virtualizers (like VirtualBox) without massive changes to setup scripts. There’s less boilerplate, fewer little details and fewer opaque incantations that need to be uttered in just the right order. All in all, it’s a much better engineered system.

Though these were all pretty significant changes it took me less than a week to get everything done. This includes walking a teammate through both the old and new versions and troubleshooting. Using Python made the transition easier because a lot of the script code and boilerplate could be tucked into the new classes and methods with a few modifications. Most of the time was spent in figuring out what the interfaces should look like and how they should be integrated.

In conclusion, Python is a great glue language. It’s easy to get up and running with quick scripts that tie together existing programs and do some data mangling. But when your needs grow beyond scripts you can build a well-structured program or library without rewriting from scratch. In particular you can reuse large parts of the script code and spend time on the design and organization of your new applcation. On a related note, this is also one of the reasons why Python is a great beginner’s language. It’s easy to start off with small scripts that do routine tasks or work with multimedia and then move on to writing full-fledged programs and learning proper computer science concepts.

As a disclaimer, I haven’t worked with Ruby or Perl enough to make a similar claim. If Rubyists or Perl hackers would like to share similar experiences I’d love to hear.

Sunday Selection 2012-06-17

Around the Web

The Essential Psychopathology of Creativity

Andrea Kuszewski is one of my favorite writers on creativity, in large part because she references actual scientific research as opposed to blog posts and random opinions on the Internet. In this article she looks at the link between creativity and apparently detrimental psychological traits.

The care and feeding of software engineers

It’s a bit disappointing that despite how much of modern society and businesses depend on software engineers managers still need articles like this to tell them how to manage engineers. The only company I worked for did not have non-technical managers so I haven’t seen this firsthand but I’m guessing I might be the exception.

How Yahoo killed Flickr and lost the Internet

The computer industry has seen more than its fair share of companies rise and fall. While Yahoo is certainly not dead yet, it’s definitely not in its heyday. I’ve never been a big Yahoo or Flickr user, but there are lessons worth learning in this story.

Books

No videos this week because I’ve been trying to avoid videos and TV and focus on reading more books.

Accelerando

I first read Accelerando a few months and I’ve been re-reading it over the last few days. It paints an interesting view of the evolution of the human race in an era of intelligent machines and accelerating technological change. While the future it shows can be terrifyingly alien, I personally also find it very interesting and hopeful.

Still Alive

Rumors of my demise are greatly exaggerated. To be honest, I always feel a tinge of guilt and regret whenever I write a post along the lines of “I’m alive” or “I’m back”. Generally it means that I’ve spent the preceding few weeks in some form of pseudo-business, done some work, probably watched far too much TV and generally spent more time consuming than creating. Oh well, what’s done is done.

As I said, I am very much still alive (not quite kicking, but I’m working on that). It’s summer which means it’s warm outside and so I’m increasingly inclined to spend time inside. I don’t like the heat very much. While I’ve been gone I’ve been thinking about a number of things of varying levels of importance to me (and to you, my dear readers). So here’s a quick brain dump, in no particular order.

It’s been a while since I learned a new programming language. I’ve been using C and Python extensively and while I like good systems and scripting languages as much as the next hacker, it’s a bit like eating only whole wheat bread with Nutella. Not that there’s anything wrong with whole wheat bread or nutella, but I am craving a bit more variety. I’ve been looking at more exotic sources of nutrition, mainly Haskell and Clojure (nothing like a good Lisp to spice things up). Real World Haskell has been sitting idle on my desk for far too long – I stalled at chapter 4 and it’s about time I picked it up again. I’m considering grabbing a copy of Joy of Clojure too.

While writing code is certainly fun, I do missing writing words. And no, I don’t mean words meant for publication in a scientific journal (see whole wheat bread and Nutella above). In particular, I’ve been wanting to tell some good stories. I’ve always loved books and television and movies but it took some binge-watching of Doctor Who to help me realize that what I really like is a good story. And I like telling them as much as I like hearing (or seeing, or reading) them. It’s been entirely far too long since I wrote any sizeable amount of fiction and I can feel my storytelling muscles atrophying. If I put it off for much longer all I’m going to be capable of is Michael Bay-esque explosive blockbusters (though that might nicely supplement my starving grad student’s salary). I’ve been thinking about doing NaNoWriMo this year. NaNoWriMo sounds like a writing marathon and like all sporting events, training helps. I’ve always considered my blog to be training for non-fiction writing (and it’s helped) so maybe a similar fiction-writing training routine might help. Speaking of blogging, I miss it too. Writing really is a great way to sort out my ideas and think aloud (so to speak). So more of that too.

In other news, this blog runs off WordPress.com and I pay for mapping the Bytebaker.com domain to their servers. Apparently this will expire in about two weeks. I’ve been barking on and off about the need for next-generation content management systems that allow for more than a blog/static-site dichotomy. Given that it’s summer and I have a solid deadline this might be a good time to bite the bullet and roll my own. I did a half-hearted attempt a few years ago and round two has been long overdue. I’m still working out just what I want from this new system, but I have some cool ideas (mostly culled from other places). More on that later.

On a mostly unrelated note I tried out a new coworking space a few blocks from my place. It’s called the Popshop and seems to be run by a bunch of Cornell seniors. It’s pretty decent, they have lots of markers, whiteboards, air conditioning, a couch and a 3D printer. But the chairs suck so I may not be back too often. I’m also more in favor of quiet and isolated working spaces. I do spend most days working in an open plan setup, but we each have a lot of space to ourselves and there isn’t a whole lot of social interaction. I suppose coworking spaces are great if you’re looking for people to bounce ideas off but I prefer isolation when it comes to actually pumping out the code (or the words).

To recap: I’m alive. I’m looking forward to lots more hacking and writing in the near future. Coworking might be cool, but I’ll stick to my office for now. See you all tomorrow.

Grit for Programmers

It turns out that the best indicator of success isn’t IQ or natural talent or how well off you were at birth. Rather it’s something called grit – the perseverance and passion for long-term goals. Grit requires a clear goal, self-confidence and a careful balance between stubborness and flexibility. For the last few months I’ve been living one of the most productive (and most challenging) times of my life. I’ve been building a system that has more parts, does more things and is much larger than just about anything I’ve built before. It’s been challenging and rewarding work and I couldn’t have done it without lots of support from great mentors. As I’ve stumbled, fallen down, hit brick walls, picked myself up and kept going I’ve been wondering – does grit apply equally to programmers and success in building good software?

Programming culture is generally synonymous with hard work and long hours — death marches, all-nighters, 80 hour work weeks, we do them all. But we’re talking about grit here, not masochism. Grit isn’t strictly equal to working obscenely hard, long hours. Part of the problem with thinking about grit in relation to programming is defining what success means for a programmer. Is your definition of success simply finding a working solution? Does it mean finding the most efficient solution? Are you successful if you cover every single edge case or is it enough to just take care of the most common ones? Is your program really better if it handles everything you could throw at it or should you handle core uses cases well and fail gracefully on the others? Part of the problem of coming up with a good solution is asking the right question. This is especially true of building software. However merely coming up with the right question requires a certain amount of grit. We need the patience to look beyond the obvious problems and solutions and ask the hard questions.

So now we’ve found the right question and defined bounds on the possible solutions. What next? How does grit help with the actual act of writing code and building stuff? Programming is not easy. It can be fun and exciting and uplifting, but sometimes it is downright hard and depressing. Sometimes we spend hours sifting through possible solutions before hitting upon the appopriate one. Sometimes we spend several intimate hours with a debugger tracking down pointer bugs before finding that one variable we forgot to initialize. Being tenacious and persistent in the face of seemingly unrelenting roadblocks is not an added benefit for a programmer – it is a bare necessity. When it comes down to the act of sitting down, writing and debugging code grit is not optional. Without it not only can we not be good programmers, we can’t even be an average ones.

But if our goal is to be a good (maybe even great) programmer, then grit will continue to help. One of the qualities of good programmers is that they get a lot of stuff done. In particular they do a lot that isn’t strictly their job. This includes fixing and extending their tools and improving core infrastructure. They do this even if they aren’t in charge of infrastructure because they realize that their code depends on what’s underneath. Grit is the difference between waiting for someone else to fix the annoying bug in the library that you depend on and diving in and fixing it ourselves. When Steve Yegge talks about the difference between “superhumanly godlike” and “smart”, grit is a part of what he’s talking about. Not that there’s anything wrong with being smart, but it might not be enough. Of course to cultivate that level of grit we need to cultivate a good deal of courage. Diving into someone else’s code and fixing it can be a daunting task but it’s one that has to be mastered.

While I’ve always liked programming it’s taken me a long time to understand the importance of grit. When you do something because you like it (mostly) it’s tempting to stay away from the parts that are painful and hard. For a long time I avoided writing large programs because I was afraid of all the complexity that was involved. I was afraid of becoming familiar with complex algorithms because I was afraid of the possibility that I’d get it wrong. I understand now that I can’t become a good programmer if I don’t push myself to do the things that I consider hard and dislike. I need to have the grit to handle large complex problems and spend the time to understand and apply advanced algorithms. The good news is that just like perseverance and discipline, grit can be trained and improved. I’m no longer as afraid to dive into unknown codebases as I was a few months ago. I now find it much easier to hold complex code paths in my head. I’m certainly far, far away from being superhuman, but I try to suck a little less every day.