Я узнаю о составном шаблоне дизайна, и я не понимаю, как я могу обрабатывать каждый компонент одинаково (Лист и композит), когда каждый раз, когда я пытаюсь добавить или удалить компонент из листа Я должен получить ошибку (или ничего не должно произойти). Кажется, это ужасный дизайн для меня, потому что он нарушает правило наследования, чтобы лечить объекты одинаково. Единственный способ - это каким-то образом отличить Композит от Листа и всегда знать, с чем я работаю. Но это возвращает меня к исходной задаче ...Правильный способ использования композитного рисунка
Компонент:
public abstract class Equipment {
private String name;
protected Equipment(String name){
this.name = name;
}
public String name(){
return name;
}
public abstract int power();
public abstract double netPrice();
public abstract double discountPrice();
public abstract void add(Equipment equipment);
public abstract void remove(Equipment equipment);
public Iterable<Equipment> createIterator(){
return Collections.emptyList();
}
}
Композитный:
public abstract class CompositeEquipment extends Equipment{
private final List<Equipment> elements;
protected CompositeEquipment(String name) {
super(name);
elements = new LinkedList<>();
}
@Override
public double netPrice() {
Iterable<Equipment> iter = createIterator();
double total = 0;
for (Iterator<Equipment> i = iter.iterator(); i.hasNext() ;) {
Equipment next = i.next();
total += next.netPrice();
}
return total;
}
@Override
public Iterable<Equipment> createIterator() {
return elements;
}
@Override
public void remove(Equipment equipment){
elements.remove(equipment);
}
@Override
public void add(Equipment equipment){
elements.add(equipment);
}
}
Лист:
public class FloppyDisk extends Equipment{
public FloppyDisk(String name) {
super(name);
}
@Override
public int power() {
return 1;
}
@Override
public double netPrice() {
return 3;
}
@Override
public double discountPrice() {
return 2.2;
}
@Override
public void add(Equipment equipment) {
//we well do nothing here because thats the final element of the tree
}
@Override
public void remove(Equipment equipment) {
//we well do nothing here because thats the final element of the tree
}
}
Проблемы я вижу:
public void extendTheTree(Equipment equipment){
equipment.add(new CompositeWithLeafs()); //lets hope it is a Composite not a Leaf!!!
}
Так как я должен использовать этот шаблон, то или в каком-то сценарии ??? Единственное решение, которое я вижу, это избавиться от концепции Leaf и использовать только Composits.
Вы хотите переместить методы 'add' и' remove' в класс 'CompositeEquipment'? – Tomasz
@Tomek Да, 'add' и' remove' не должны быть в компоненте, они не должны быть частью интерфейса Component. Они должны быть определены только в Composite. После того, как вы это сделаете, вы обнаружите, что некоторые дизайнерские решения приходят естественным образом. – xnakos
, но затем вы теряете прозрачность, потому что у листьев и композитов теперь есть разные интерфейсы. Это не то, о чем эта картина. Наверное, я пытаюсь съесть пирог и пирог. – Tomasz