4 ms·
Off-topic (or maybe not), the title reminds me of a coding API/interface design issue I often encounter, and I'm never able to resolve without finding whatever
by fizixer 9y ago
Off-topic (or maybe not), the title reminds me of a coding API/interface design issue I often encounter, and I'm never able to resolve without finding whatever I end up with as ad hoc at best.
To give a contrived example (note: the example is about a pre-condition-like check, but that's not always the "intermediate action").
Let's say I design a sort function. It takes a linear collection (like an array or list) and returns the same (sorted). Let's say I need to carry out an intermediate action (intermediate as in, between the calling code before sorting and the sorting algorithms itself) that I need to check if the collection is already sorted, and return the collection as it is without invoking the sorting code.
The design issue I have is: should the check be inside the sort function or in the calling block just before the sort call?
It might feel like the validation squarely belongs inside the sort function but, besides this example being a bit contrived, there is a solid counter argument to be made that 'the job of the sort function is to sort'. If I am a sort function, I sort. You give me a collection, I return a sorted collection. Don't encumber me with extra checks of validating if the collection is worth sorting, or some other stuff.
This is a general problem not specific to coding. In an interface between a manager or a team-lead and the engineer, there are often situations when the engineer says "It's my job to do this, you give me the task in this, such-and-such prepackaged, form and I will return you the results." Later, the lead wants the engineer to improvise a bit and do this extra thing, an intermediate action, before actually doing the task. This "intermediate action" fits squarely in neither the lead's or the engineer's roles. Ignoring the tilted-balance-of-power in which usually the engineer ends up doing what's slightly vague, which I consider an ad-hoc solution, the engineer could just as well say "Why don't you do it?".
I guess there's a 3rd possibility in which a 3rd party does it. So in the case of sort, we have a pure-sort function, which is called by "an outer-sort" function which has all the checks, and if they all pass, only then the pure-sort is called. And that outer-sort is called in the calling code instead of calling pure-sort directly.
Which one of these is the best? most optimal? correct? What should even be a criteria for judging the implementation of such a scenario? I don't know.
edit: another example, you have an in-place sort impl. and a non-in-place sort impl. In the calling code you wish to switch between the two making sure it's always non-in-place. Should you wrap the in-place sort in a make-a-copy-before-sorting wrapper? or should the in-place impl do it itself just before returning? or should the calling code handle the two types of sort with some if check?