Что происходит, когда конструктор частично преуспевает перед выдачей исключения? - PullRequest
4 голосов
/ 03 августа 2011

Предположим, у меня есть следующий базовый класс:

public class RootClass {

  private List<RootClass> children = new ArrayList<RootClass>();

  public RootClass(RootClass parent) {
    if (parent != null) {
      parent.addChild(this);
    }
  }

  public void addChild(RootClass child) {
    children.add(child);
  }

}

И у меня есть следующий дочерний класс:

public class ChildClass extends RootClass {
  public ChildClass(RootClass parent) {
    super(parent);
    doInitialization();
  }

  private void doInitialization() {
    //Might throw an unchecked exception
  }
}

Теперь предположим, что я создаю экземпляр ChildClass, который генерирует исключение, но перехватывается за пределами конструктора (где-то в глубине кода, так далеко, он не знает, что ChildClass имеет не был полностью построен). Теперь родительский элемент имеет в своем списке children ссылку на ChildClass, для которого не был запущен конструктор.

Как следует обращаться с этими ситуациями? Это просто плохая схема дизайна? Или это имеет хоть какой-то смысл? Я не хочу реорганизовывать приложение целиком, чтобы добавить дочерний элемент к родительскому элементу после завершения работы конструктора.

Ответы [ 2 ]

2 голосов
/ 03 августа 2011

В качестве общего принципа следует избегать утечки значения this из конструкторов любой ценой. В этом случае родительский объект будет иметь ссылку на полу-построенный объект. Это должно быть закодировано в вызывающей стороне как, например. parent.addChild (new Child ()) вместо автоматического добавления.

1 голос
/ 03 августа 2011

Если это:

 private List<RootClass> children = new ArrayList<RootClass>();

Если бы вы были статическим полем, вы бы просто слили полуинициализированный объект в дикую природу. Поскольку это не так, это просто не будет иметь никакого значения.

У вас есть проблема, только если эта ссылка просочится куда-то за пределы объекта, тогда у вас будет наполовину инициализированный объект, ожидающий проблем в вашей системе. Пока вы уверены, что ссылка никуда не выходит из себя, это все хорошо.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...