复合策略模式 - java - 这段代码有多糟糕?
这个问题是我之前帖子的延续: 访问者模式实现在 java 中-这看起来怎么样?
在重构我的代码时我有点困惑。 我正在尝试将我的访问者模式(在上一篇文章中解释)转换为复合策略模式。 我正在尝试做这样的事情:
public interface Rule {
public List<ValidatonError> check(Validatable validatable);
}
现在,我将定义这样的规则:
public class ValidCountryRule {
public List<ValidationError> check(Validatable validatable) {
// invokeDAO and do something, if violation met
// add to a list of ValidationErrors.
// return the list.
}
}
现在,我可以验证两种不同类型的对象。 这两个可能完全不同:假设我有一个 Validatable
的 Store,然后有一个 Validatable
的 Schedule
。 现在,如果我要编写一个如下所示的组合:
class Validator implements Rule {
private List<Rule> tests = new ArrayList<Rule>();
public void addRule(Rule rule) {
tests.add(rule);
}
public List<ValidationError> check(Visitable visitable) {
List<ValidationError> list = new ArrayList<ValidationError>();
for(Rule rule : tests) {
list.addAll(rule.check(visitable);
}
}
public Validator(ValidatorType type) {
this.tests = type.getRules();
}
}
我将定义一个 enum
来定义一组检查去哪里......
public Enum ValidatorType {
public abstract List<Rule> getRules();
STORE_VALIDATOR {
public List<Rule> getRules() {
List<Rule> rules = new ArrayList<Rule>();
rules.add(new ValidCountryRule());
rules.add(new ValidXYZRule());
}
// more validators
}
最后,我会像这样使用它:
Validator validator = new Validator(ValidatorType.STORE_VALIDATOR);
for (Store store : stores) {
validator.check(store);
}
我有一个奇怪的感觉是我的设计有缺陷。 我不喜欢我的 Rule 接口需要 Validatable 的想法。 你能建议我如何改进这个吗?
感谢你的帮助。
This question is kind of continuation to my earlier post: Visitor pattern implementation in java- How does this look?
I got a bit confused while refactoring my code. I am trying to convert my visitor pattern (explained in the prior post) into a composite strategy pattern. I am trying to do something like this:
public interface Rule {
public List<ValidatonError> check(Validatable validatable);
}
Now, I would define a Rule like this:
public class ValidCountryRule {
public List<ValidationError> check(Validatable validatable) {
// invokeDAO and do something, if violation met
// add to a list of ValidationErrors.
// return the list.
}
}
Now, I could have two different types objects to be validated. These two could be completely different: Say I have a Store that is Validatable
, and then a Schedule
which is Validatable
. Now, if I would write a composite that would look like this:
class Validator implements Rule {
private List<Rule> tests = new ArrayList<Rule>();
public void addRule(Rule rule) {
tests.add(rule);
}
public List<ValidationError> check(Visitable visitable) {
List<ValidationError> list = new ArrayList<ValidationError>();
for(Rule rule : tests) {
list.addAll(rule.check(visitable);
}
}
public Validator(ValidatorType type) {
this.tests = type.getRules();
}
}
I would define an enum
that defines what set of checks go where...
public Enum ValidatorType {
public abstract List<Rule> getRules();
STORE_VALIDATOR {
public List<Rule> getRules() {
List<Rule> rules = new ArrayList<Rule>();
rules.add(new ValidCountryRule());
rules.add(new ValidXYZRule());
}
// more validators
}
and finally, I would use it like this:
Validator validator = new Validator(ValidatorType.STORE_VALIDATOR);
for (Store store : stores) {
validator.check(store);
}
I have a strange feeling that my design is flawed. I am not liking the idea that my Rule interface expects a Validatable
. Could you please suggest how I would improve this?
Appreciate your help.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
当我第一次学习设计模式时,我一直在努力寻找使用它们的地方。 从那时起我就了解到过早的“模式化”有点像过早的优化。 首先,尝试以直接的方式进行,然后看看会给您带来什么问题。
尝试使用最少的接口和子类进行设计。 然后应用适合您发现的明显冗余的任何模式。 我从这篇文章和上一篇文章中得到的印象是,您可能过度构建了代码。
When I first learned about design patterns, I kept trying to find places to use them. I've since learned that premature "patternization" is kind of like premature optimization. First, try to do it in a straight-forward way, and then see what problems that gives you.
Try to design with minimal interfaces and subclassing. Then apply whatever pattern may be appropriate for the obvious redundancies you find. I get the impression from this and the previous post that you may be over-architecting your code.
将 Validatable 替换为泛型类型参数 T 以使验证框架类型安全。
让我们用 ValidationStrategy 接口扩展我们的框架:
我们正在处理由“? super T”限制的规则,因此我们可以将 Animal 的规则添加到 Dog 验证器(假设 Dog 扩展 Animal)。 验证器现在看起来像这样:
现在我们可以像这样实现一个示例 DogValidationStrategy:
或者,就像在您的示例中一样,我们可能有一个提供多种狗验证策略的枚举:
Replace Validatable by a generic type parameter T to make the validation framework type safe.
Let's extend our framework with an interface ValidationStrategy:
We are dealing with rules bounded by "? super T" so we can add a rule for Animal to a Dog Validator (assuming Dog extends Animal). The Validator now looks like this:
Now we can implement a sample DogValidationStrategy like this:
Or, like in your sample, we may have an Enum providing several dog validation strategies: