Alternative to DoTheSimplestThingThatCouldPossiblyWork
This is not a pattern but at least that's what I'm doing and I think a lot of other people do like me.
I was wrong sometimes in choosing what might work well, but in those cases DoTheSimplestThingThatCouldPossiblyWork
wouldn't have helped, and when I had to refactor I was able to reuse a large part of the previous work. -- CostinCozianu
Actually, I think it is
a good pattern for areas that you aren't familiar with. If you don't know exactly how to confront a problem, start by doing something that might work then analyse your solution.
Let's take an example: suppose that I don't have a qsort() handy and ready to use - this is just for the purpose of this discussion; since Java 2, all the relevant development platforms seem to have it.
So I have to write a sort() function. The SimplestThingThatCouldPossiblyWork
would obviously be:
for i ...
for j ...
But I just can't do just that. The project might be able to do just fine with for i ... for j ...
and 4 lines of code can be written in 1 minute, and testing and debugging that would be a no brainer (if needed at all).
So I write the qsort(), which is more expensive to write; the test would be much the same, but a lot harder to debug and/or code inspect; if needed, I might just write a modified version of qsort() that prevents data anomalies from getting qsort() to the O(n^2) behavior; after all, references can be easily found on the web and you can get it from lots of books.
In designing a database schema, DoTheSimplestThingThatCouldPossiblyWork
would be one huge table (and I've seen that in practice!!!) optionally with a couple of minor lookup tables on the side, and all guards left down (any integrity constraints left for the application to apply).
So the general idea is that I use my intuition and my training in ComputerScience
to guess what is the thing that might work well, and try to start with that. If I choose the simplest thing, chances are (>50%) that I'll have to replace it anyway with the more expensive solution.
does not mean that you should do the simplest thing which will compile and run
. Let's say you were building a database engine, and needed a sort to work on result sets. Would you even consider using a bubble sort? Of course not, it couldn't possibly work
. Let's say it's a more typical application - you have to consider if it will possibly work. If you're sorting 5-10 items, then why not use a bubblesort (presuming no language feature was available)? Note, by the way, that this discussion seems to be more about whether to OptimizeLater
than whether to DoTheSimplestThingThatCouldPossiblyWork
. -- PeterCrabtree?
Actually, DTSTTCPW says exactly that (that which you say it's not saying). Having a trail of interaction with XP promoters, and having studied the material promoting Xp, I think I know exactly the spirit of DTSTTCPW. In particular, RonJeffries responded to a challenge of mine following DTSTTCPW, see http://www.xprogramming.com/xpmag/acsDiningPhilosophers.htm, so he wrote just the thing that can barely compile and run.
I'm not saying that DTSTTCPW is not applicable in specific contexts; I'm saying that DoTheThingThatMightWorkWell is an alternative that can work just as well if not better in (possibly different) contexts. -- CostinCozianu
Do this for me. Test both algorithms. Report back how big the array has to be before qsort is actually better. Also report how long the exercise of writing qsort took. Reflect on what you could have done that would have been more valuable.
I did just that when I'd written a sort program for the old MS-DOS (the 6.2- 7.0) in Borland Pascal (it didn't have a library sort, or I just didn't know about it at the time). I couldn't say that the MS-DOS sort results were too encouraging, probably it was in there just as an exercise. Guess what, I tested the WinNT sort later and it was much improved, but still very slow. How about you?
Actually, the simplest thing would be to use the qsort library function.
Agreed, but remember that before Java 2 you didn't have an equivalent of the qsort function in Java, so the example is realistic, but it is just an example for this discussion only.
I agree that a lot of people use this pattern after hearing about DoTheSimplestThingThatCouldPossiblyWork
. To the XP newcomer, it seems like a sensible hedge. I think it is a pattern, not an AntiPattern
, although in my experience DoTheSimplestThingThatCouldPossiblyWork
is a more effective way of working.
I have an objection to the database examples, though. DoTheSimplestThingThatCouldPossiblyWork
is often misunderstood, and I think that's what has happened here. It doesn't mean DoTheEasiestThingThatCouldPossiblyWork
, as in the first DB example. It doesn't mean "ignore failure modes" or "assume valid data," as in the second. It means that the software you design should be as clean as possible, meet the feature and quality requirements, and not anticipate future needs. See SimplicityRules
As for the qsort example, I have a real-world anecdote related to that. I had to implement a sort routine in Java 1.1. I wrote a bubblesort, as it was the simplest thing that could possibly work. It did work. I considered the upper size bound of my input data set. I ran the tests and checked performance. No performance hit was expected, and none was seen. That bubblesort is still in the software, and the software is still working fine. By not looking up and transcribing a qsort, I saved myself significant time.
Jim, even for 100 objects "for i, for j" takes significantly longer in Java. Yeah, but we were only dealing with 5-10. :)
Costin, I read your quicksort story, but I didn't reach the same conclusion that you did. If writing the simple sort takes one minute, and the same tests can be used for both the simple sort and the quicksort, then what reason do you have not
to do the simple thing first? If you discover that the simple thing is too slow, it'll be trivial to rip it out and replace it with the quicksort, and it will only have cost you one minute.
Maybe it depends on the difference in simplicity between the two solutions. If the simple solution will take one hour and the more-complex-but-probably-necessary solution will take two hours, maybe you're better off jumping straight to the complex one. What if the simple one costs one hour and the complex one costs ten hours?
Adam, that's what books are for. DonaldKnuth
and many others teach us how to analyze problems, how to choose algorithms that work well, how to implement them, and how to predict their behaviour both in average and in worst conditions. That's what DoTheThingThatMightWorkWell
is all about. DoTheSimplestThingThatCouldPossiblyWork
jumps over education in computer science, years of experience and many other factors. Only if I start to calculate how much simpler is a simple algorithm and how safe the software will be by employing a lower quality solution (maybe the original developer will no longer be on the project when things start breaking ), I'll be wasting more time that it's worth it, and, frankly, I think also of my little person. I don't think I could ever slip well after I've written a for i, for j
sort, or other comparably clumsy and simple solution. A simple solution is always welcomed and take precedence as long as it might work well
, not just could possibly work
. -- CostinCozianu
DoTheSimplestThingThatCouldPossiblyWork jumps over education in computer science, years of experience and many other factors.
Nah. ;) We expect that you'll use
your education and experience when trying to figure out whether an approach could possibly work. -- AdamSpitz
If you say so. But it looks like the accent is put on simplest
as opposed to the work
, and whether it works well or it barely works is left as a refactoring exercise, because you're going to do design mistakes anyway. Therefore I say: do the thing (not necessarily the simplest but also not necessarily complicated) that might work well
(some accent has to be on quality). -- CostinCozianu
Programmers often do unnecessarily complex things. Programmers rarely do things that they know won't work. I learned a lot from XP's emphasis on simplicity, and I'm really not worried that anybody is going to use DTSTTCPW to justify doing simple things that don't work.
What do you think the difference is between "working" and "working well"? Do you think JimLittle
's bubblesort solution worked well?
Adam, you seem to know a lot about programmers in general. My strict experience (and I don't know of any serious statistic in this regard) is that programmers very rarely do unnecessarily complex things unless indoctrinated by fashionable currents of opinions. Also, many programmers very often tend to write code at the minimum level of quality. Not to mention that there are plenty of programmers out there who have no clue how to write a quicksort, but are experts in the hype du jour
. Not that they would use DTSTTCPW as a justification, but that's their way of life. And responding to your last question, I see no justification whatsoever for anyone using bubblesort, under any circumstances. -- CostinCozianu
My apologies. If you're working with programmers who are good at keeping things simple but have trouble remembering to do things that work, then you should definitely put the emphasis on working well.
I'm sorry that you think JimLittle
's bubblesort solution didn't work well. Thank you for your time.
Also, is the qualifier well used by the client or the developer? If it is used by the developer, does it generate value for the client? If not, is something that works well actually better than something that works?
Is a BMW better than my Plymouth Neon? Of course it is. My Neon works while a BMW works well. But a BMW costs much more than it's worth for my needs. In software unlike in cars, not every user can tell if a software works well, how well it works, how much better or worse it is comparing to alternatives. And more often than not custom made business software is not bid for in an open market where the consumer is empowered to make real decisions. If a BMW would cost only $5000 more than my Neon I'd buy the BMW. If I can give my client quality software without even making him pay more, do I need to ask for his permission? No, I just DoTheThingThatMightWorkWell
. -- CostinCozianu
What is simplest is relative to the developer. If you've done a qsort 10 times, then to you it is likely to be simple even if it is not for someone else. And of course work is also relative. What some people accept as "working" is astonishing. But that's the problem with simple rules. There is always an out because you can always say how it wasn't applied correctly and there's no way to know if it is correctly applied. -- AnonymousDonor
I think qsort is a bad example for this. Are you going to spend a great deal of time trying to decide for yourself how to DoTheThingThatMightWorkWell
and write the code yourself or wouldn't it be better to simply do a few minutes of research and use someone else's qsort code? -- BlakeMason
Sometimes, patching other's people packages to fit your current context is not worth the effort compared to writing everything from scratch.