D
Daniel Pitts
That's like saying Oranges taste better than Apples because you have tomarkspace said:Yes, that's primarily the use-case I was thinking of. Of course there
could be more complex interactions where decorators are not suitable.
Primarily because they only do modify "input and output" and often only
deal with one public method at a time, I think they're more encapsulated
than certain other types of composition.
peel them
Strategies can be very tightly encapsulated, and Decorators are subject
to Object hierarchy dependencies which can increase complexity.
For example, recently I added a GZIP filter to one of my webapps. It
worked well, except when another filter was triggered in the wrong
order, and it tried to modify the GZIP data, rather than the underlying
data. If there had been a "Content-Encoding Strategy" that I could have
set to a GZIPContentEncoder, it would have been a non-issue.
Well, in either case, both patterns are valuable, and I think Strategy
tends to be under-used. I suggest playing around with it to see how it
works out.
If you find you have a tree like this:
[A]
/ \
[C]
where A, B, C are classes, and B methods overrides are a disjoint set of
from C methods overrides, try instead to make it a strategy (or several
strategies even).
Yes, you end up with more "classes":
[A] +
/ \ / \
[A'] [A''] [C]
where A is composed of S and S' objects, S/S' are abstract or interfaces
and the default impl in the old system for A is now in A' and A''. The
overridden methods in B/C remain the same.
Just try it, and see where it leads you.