Since starting this blog it has made me think about regular activities and wonder if they can teach me any lessons for writing better software. In the last couple of years jigsaws have gone from not on being my radar to a fairly regular thing. I often pick colourful, geometric or architectural one. Although there’s a big chunk of visual pattern matching going on there’s also prioritising and matching techniques going on. Maybe we can learn something here.
Jigsaws
My normal procedure for a jigsaw is to sort out the edge pieces, the same as everyone else. Then flipping everything face up so I can see the picture. Next I separate the pieces out into smaller piles based on colours and patterns. I assemble the edges as much as possible, normally I’ve failed to find some of them in the first sort. Then I iterate round the piles from earlier picking smaller ones with easier matching first. At the start there are many pieces to match against, even with the sorting, but there are gradually less and the matching gets faster. At the end there is a rush when just a handful of pieces and holes left.
Thinking about the process:
- Baring occasional missing pieces, you know that there is a place for everything and everything has a place. There is little point in my agonising over finding the piece for one exact spot or for finding the exact spot for one particular piece. Moving forward on any part of the puzzle reduces the number of pieces to search through and makes future progress easier. Picking the easiest part first makes sense.
- With 500+ piece puzzles it’s not possible for me to lay all the pieces out at once, my table just isn’t big enough. I’ve got to divide it into a number of smaller puzzles. If I manage to separate the pieces well then my search space will be much smaller and I can work faster. However sometimes I’ll make the wrong choice about which piles to make and it’s not easy to match pieces. Resorting into different piles can make it better.
- It’s not uncommon to look through 200-300 pieces trying to find a match. Given all the searching it’s worth making the searching as easy as possible. I can search through a regular grid of pieces faster so invest time laying everything out.
Lets see if we can derive some lessons:
- Divide the problem so it’s easy to solve.
- Organise the sub-problems so they’re quick to solve.
- Start with the simple problems.
- Use progress to help make the problem easier.
Software development
Obviously software development isn’t a jigsaw puzzle. I don’t just want to think about the similarities between the two but the differences as well.
Often in my software projects we didn’t know what the complete thing is going to look like. We weren’t given a solid design either visually or functionally. There may have been general visual ideas and rough ideas about functionality but there was an expectation of prototyping and experimentation. That’s part of the business fields and companies that I’ve worked with. Without a guarantee that there is a way forward you risk not be able to get to a satisfactory solution. If you don’t know exactly what’s being made or that you can definitely make it then you can reduce you risk by exploring those parts first. Doing the easiest bits first and then finding that the hard bits are impossible is a waste of time.
On the other hand starting with the hard bits has it’s own problems. By definition, the hard bits are hard. At the start of a project there’s normally be a bunch of setup and ground work. That might involve setting up the build script and getting some initial libraries working. If you’re trying to do the hardest bits whilst simultaneously doing the ground work then the latter my suffer. Metaphorically I would try and do some of the edge first. Pick something easy. Maybe that helps define the boundaries of the project: making an executable, pulling in the input (without parsing), and pushing out the (dummy) output. Then switch to the hard bits and make sure they are possible.
With a jigsaw you tend to build momentum over time as the the number of pieces to check goes down. With software the opposite can be true. The more you have built the more existing code you have to integrate with. If you let it get away from you technical debt can be a serious problem. Building low quality code that makes for difficulties in the future means everything will be getting harder as you push towards delivery. This is a positive feedback loop so problems tend to create more problems.
If you do have to make choices about where to spend your time try to get the interfaces right. With low quality implementations but high quality interfaces it’s easy to go back and fix things later. Maybe your first version of the code is, say, slow but it can always be replaced later.
Concentrate responsibilities where you can. Have specific classes, functions and modules to perform tasks when you can rather than spreading it out. This means when you need to make changes, which seems to be the only constant sometimes, it only has to be done once. Collecting code together is also a great opportunity to compare how things are being done and notice patterns. This can lead to further consolidation.
At some point you might find that the original set of interfaces aren’t going to work. Maybe two systems simply have to share information and therefore classes need to be combined. It might be worth a prototype first but making the effort to refactor the code can be better than working with a hack. If that hack gets copied throughout the codebase then fixing that becomes much harder.
In the end
Is it worth analysing everyday activities? At the very least it gives me some practice analysing a process. I think there are more difference than similarities between jigsaws and software. However thinking about those differences can highlight what you do need to think about with software.
Leave a Reply