Assume we have an abstract class having several concrete classes which interfaces publish an information under several equivalent forms, with the difference that each class has a preferred form which can be consulted at no cost while consulting the others might require a time-consuming computation. How to implement a strategy selecting an algorithm based on this “affinity”of one class for one information form?
Example
The original example is a complicated example of a very specialised field, so I will do my best to figure out an example that will be familiar to most programmers.
Assume we have an abstract class representing I/O devices which has two concrete subclasses, one for char-based devices and one for block-based devices. Each class provides block-based access and cahr-based access, but each class has an affinity to one of these methods: block-based access is preferred for block-based devices, etc. Say, we want to implement a copy procedure, so that, if the source and the target devices are block-based then the copy is performed block-per-block, in all other cases, a char-by-char approach is preferred.
Discussion
Assume now we have not only I/O devices but several abstract classes offers access to several logically equivalent methods, but whose implementation differ greatly in perormance, thus displaying a greater affinity to one method over the others.
We want to implement a strategy working on an aggregate of such classes and selecting an algorithm taking the affinities of these classes into account.
Because of the combinatoric complexity brought by the aggregate, the visitor-pattern does not seem useful here.
Question
How can each concrete class expose its affinity for one or the other access method in a way that is useful to a strategy component picking up an algorithm suited to these affinities? The combinatorics yield a large number of combinations of affinities and the strategy only needs to consider a few “lucky cases”and use a generic algorithm to handle the vast majority of combinations.
enum
constant) yourself, i.e. outside the semantics of the interface itself.