While I see the need for reducing edge cases, I somehow have difficulties grasping “taste” as shown there. Seems to me rather subjective and hard to convey.
Linus is saying: Make the happy path the only path whenever you can, that way you have only one path to think about and to test. Each if() increases the number of paths through the function.
He’s also saying a little more, but that’s the core, and it’s not subjective: Count the number of paths through a function, low is good. Now, some 4s may be better than other 4s and then you have to discuss subjectively, but that issue happens seldom. Usually you’re looking at 2 vs 12 or something else crude.
Those who like this kind of thing might want to reread Christopher Seiwald’s https://www.perforce.com/resources/seven-pillars-pretty-code — the “fight changes of indentation” bit is excellent advice and generally leads to few paths through the function, and the “exceptions to the top” shortens many of the paths that cannot be eliminated.
Thanks for that link, it’s helpful!
The example there about edges on an array is something I’ve had to directly deal with myself when I implemented a multidimensional image-processing function for GNU Octave. The problem is to find connected components in a binary image, where voxels are either 0 or 1. You want to find all the islands of ones, and you want to be flexible if diagonals count as being connected or not.
The problem, of course, is that along the edges you don’t want to check for neighbours outside of the image boundary. I found no good way to do this for an n-dimensional image, after a few attempts of writing very complicated code. In the end, I ended up padding the whole image with a boundary of zeros, iterating over the padded image with an if(current_voxel) conditional that skipped checking for lit neighbours around the boundary, and when checking for lit neighbours at the original image’s boundaries would give no neighbours at the padded zero boundaries.
The code was cleaner, but I incurred a big realloc, because N-dimensional images in Octave are stored as contiguous Fortran-order (column-major) arrays. I’m still looking for a better solution to this problem.
So, how do you do this cleanly?
I recently ran across a blog post that claims Julia’s ‘cartesian iterators’ make this less painful/ugly than normal (scroll down to “A multidimensional boxcar filter”). I haven’t put them to any serious use myself yet though, so I can’t really vouch for this either way.
I’d use a union-find algorithm along one dimension at a time. Diagonals would simply be another set of axes.
Can you explain this more? Note that iterating one dimension at a time is a bit tricky given that the thing is n-dimensional to begin with.
Yeah, I felt the same way: https://news.ycombinator.com/item?id=12794250
Good taste is subjective, just like good vs. bad art is subjective, and yet most people tend to agree which is which :). Writing good code means writing for the benefit of human readers, so it’s no surprise that you need to think in terms of fuzzy human grokkability.
For the interested, Zen and the Art of Motorcycle Maintenance is basically an extended discussion of exactly this concept. Its central theme is that quality as a concept is undefinable yet deeply important.