Good code is elegant.
Good code is short and to-the-point and offers the simplest solution to a certain problem.
Good code is easy to maintain and to understand.
What is good code??
I’ve always been trying to write the best possible code and I think in the past years I’ve learnt quite a lot on how to write code that in my opinion is good code - mainly due to guidance from great books like Code Complete and Programming Pearls and from reading other’s code (mostly id’s) to see how they write their code and from reading other’s to see how not to write code because it was hard to understand or a plain and utter ugly hack.
There always comes a moment for every programmer now and then to go out of your regular thinking patterns and reflect about all the code that you have written and really evaluate its quality, its advantages and its disadvantages.
The moment seems to be here right now for me.
In general I really hope and believe that my coding style has evolved to the better in the last years but there is certainly a lot that I need to criticize if I’m honest.
The first and biggest point is that the code I’m the most proud of seems barely readable and baffling to most of the coders I’ve talked to (- all of them to be honest).
Why?
The code I’m the most proud of is elegant, works and I can extend it easily and after reading a few bits I quickly understand its design again. It also is very complex but it arguably does an at least moderate if not good job at dividing the problems into different subproblems, defining interfaces, separating everything from each other and so on (see Code Complete for a list of things it tries to achieve and possibly achieves). The one thing it probably and quite certainly lacks is good documentation. I’m not a fan of writing lots of documentation because code changes and updating comments is a tedious process you’re often forget to do. This naturally leaves the readers of your code more confused than without misleading comments in the first place.
I’ve been trying to make my code document itself - look at DarkWar’s shell code to see what I mean: the function names are more than descriptive, the code reads like a book and it is its own flow diagram pretty much. Still people are frightened by it and most of Nexuiz’s coders are scared by the menu system I’ve written.
The problem as I see it currently is, that although I haven’t over-engineered the code, I certainly have taken too many measures to make it only work as intended. That is, the code will fail when you try to hack it - which in my opinion still should be a good thing, but apparently isn’t.
More precisely, the design doesn’t allow one to add hacks, because it’s so tight and so self-contained in its thought-model that there is only one way to make changes: make them correctly and have them fit the abstract design concept or if that doesn’t work, change and adapt the whole model to your changes.
I consider this great, since, if you know the design and the code, it prevents you from doing stupid things and provides an easy way to add features, since there are only correct ways to do it - albeit only few though.
The problem with this is, however, that you need to allow other people to hack your code and try things, as this is the way most people seem to learn and understand new designs: (intelligent) Trial & Error until they find the right solution.
If you don’t, people will be scared by your code, because from their perspective it is like a brick wall that doesn’t allow any changes to its structure.
There are two solutions for this issue:
Tell people to read your code like a book first and then start to carefully change it, but this is what I’ve been doing most of the time and it certainly doesn’t seem to work
Try to change your code to fail more gracefully and allow more hacks: soften pre- and post-conditions in functions, maybe weaken the design contracts, and so on. All in all: allow more holes in the code design.
I don’t like either solution to be honest, but I’m still searching for a satisfying answer.
I only know that writing code that allows hacks too easily is bug-prone and quite probably a hack-magnet and will lead to equal confusion among readers because of the lack of a strict (abstract) design (as was the case for me in some parts of DarkPlaces) and it makes coding-life - once you know the codebase - more difficult too, because you’ll have to fix more bugs. Writing non-perfect code can turn out fine, too, though, as I’ve experienced during Sploidz’s development - some of the designs and parts of the code are a bit hacky but all in all it still leaves a good feeling when I’m reading it and it has allowed for fast development - and Shelled’s development - server-side mostly though since the client-side really needs a rewrite -, but one has to carefully measure every hack and loophole one allows.
To sum it up before I write another ten pages, code has to be hackable and it shouldn’t provide too much resistance against bad changes and hacks at first to let people toy around with ideas and get comfortable with the code but then it should still limit them to writing good code in general by making the hacks fail in the big picture, i.e. for small hacks it should work but if you want to make it work for real, you should need to do it right and the code should also point you towards it, that is, the code layout should offer a guidance for the changes you want to make.
There is already lots of code out there that does this and also lots of code that is going to be released, so I hope that I’ll find some more insight on this soon :)
All this rant has been created from a simple insight while I was taking a break from learning for my A-level exams, and I hope that I’ll be able to investigate this some more when I’m done with my exams.
Anyway, stay tuned,
Black
PS: My first exam is in English, so this hopefully ought to be some good and valuable practice.