曾经有一位Java程序员对我说,他现在越来越频繁地采用构造函数+初始化函数的方式来准备一个对象,而不是直接在构造函数里将所有资源都准备好。谈及原因,他说道,他在GUI开发当中经常要在子类的初始化过程中调用父类的资源,而他发现子类的构造函数执行时,有的父类资源却还没构造好。
我对Java的机制并未做过深入的了解。“构造函数+初始化函数”的对象准备方式似乎违反了RAII原则。而且在C++中,当子类的构造函数开始执行时,父类的构造函数应该已经执行完毕,父类资源也应该都已经构造好了——至少我目前还没碰到反例。当然,我记得wxWidgets的文档写道,wxWidgets既支持RAII的方式,也支持“构造函数+初始化函数”的方式,并且说道有时候后者是必须的;但是我已经记不得在什么情况下后者是必须的了。
不过在前一段时间的工作中,我也不得不使用“构造函数+初始化函数”的方式来准备一个C++对象了。原因是我需要在对象的准备过程中调用虚函数,而构造函数中是不应该调用虚函数的:Never Call Virtual Functions during Construction or Destruction。有时间我得读读这篇文章。
不知是否有办法让我既能遵循RAII原则,又能将各个子类所共有的准备过程抽象到父类中呢?敲了几年的代码,还没仔细学习过设计模式。现在逐渐体会到设计的重要性了。