i've run situation in extend functionality of given class, i'm not sure of best way go this. started invoking functionality "upwards" , have switched "downwards", see issues both. let me explain mean. first, "upwards" approach:
public class parentvalidator { public void validate() { // code } } public class childvalidator extends parentvalidator { @override public void validate() { super.validate(); // code } } public class grandchildvalidator extends childvalidator { @override public void validate() { super.validate(); // code } }
this functions well, requires remember place super.validate() in method body or logic in parent class(es) won't executed. in addition, extension in manner can considered "unsafe" due fact child class replace/modify code defined in parent class. call invoking methods "upwards" because i'm invoking methods higher level classes go.
to counter these shortfalls, decided make parentvalidator.validate() final , have invoke different method. here's code modified to:
public class parentvalidator { public final void validate() { // code subvalidate(); } protected void subvalidate() {} } public class childvalidator extends parentvalidator { @override public final void subvalidate() { // code subsubvalidate(); } protected void subsubvalidate() {} } public class grandchildvalidator extends childvalidator { @override public void subsubbalidate() { // code subsubsubvalidate(); } protected void subsubsubvalidate(); }
this referring when i'm calling downwards each class invokes methods on classes "down" inheritance chain.
using approach, can guaranteed logic in parent class(es) executed, like. however, doesn't scale well. more layers of inheritance have, uglier gets. @ 1 level, think elegant. @ 2 levels, starts shoddy. @ 3 or more, it's hideous.
in addition, had remember invoke super.validate() first line of of children's validate methods, have remember invoke "subvalidate" method @ end of of parent's validate methods, didn't seem better.
is there better way type of extension haven't touched on. either of these approaches have serious flaws , i'm wondering if there's better design pattern using.
in describe first approach using simple inheritance, second approach closer gang of four [gof] called template method pattern because parent class using so-called hollywood principle: "don't call us, we'll call you".
however, benefit declaring subvalidate() method abstract in parent class, , this, make sure subclasses forced implement it. true template method.
public abstract class parentvalidator { public final void validate() { //some code subvalidate(); } protected abstract void subvalidate() {} }
depending on doing there other patterns in different manner. instance, use strategy pattern peform validations, , favoring composition on inheritance, suggested before, consequence need more validation classes.
public abstract class parentvalidator { private final validatorstrategy validator; protected parentvalidator(validatorstrategy validator){ this.validator = validator; } public final void validate() { //some code this.validator.validate(); } }
then can provide specific validation strategies every type of validator have.
if want best of both worlds might considering implementing solution decorator pattern subclasses can extend functionality of parent class , still stick common interface.
public abstract class validatordecorator implements validator { private final validator validator; protected parentvalidator(validator validator){ this.validator = validator; } public final void validate() { //some code super.validate(); //still forced invoke super this.validator.validate(); } }
all patterns have consequences , advantages , disadvantages must consider carefully.
Comments
Post a Comment