2010-12-11 125 views
27

我们基本上都知道Constructor和用户定义的Initialize()方法之间的区别。初始化()vs构造函数()方法,创建对象时的正确用法

我的问题是关注对象创建的最佳设计实践。我们可以将所有Initialize()代码放入Constructor(),反之亦然(将所有预热代码移至Initialize方法并从Constructor调用此方法)。

目前,设计一个新类,我在constructor()内部创建任何新的实例,并将其他预热代码移动到Initialize()方法中。

您认为最好的交易点是什么?

回答

23

我觉得是应该考虑多个方面:

  • 一个构造函数应该在某种程度上,它是处于可用状态初始化的对象。

  • 构造函数应该只初始化一个对象,而不是执行繁重的工作。

  • 构造函数不应该直接或间接调用虚拟成员或外部代码。

所以在大多数情况下,不应该需要Initialize方法。

在初始化涉及的不仅仅是将对象置于可用状态的情况下(例如,需要执行繁重的工作或需要调用虚拟成员或外部对象时),那么Initialize方法是一个好主意。

+0

好吧。在过去,我还倾向于在构造函数中使用'initialize()'方法,而不是直接实例化对象,就像使用工厂模式一样。你认为这是一个相关的考虑因素吗? – Ray 2017-01-26 18:59:41

3

最近我发现自己在思考这个问题(因此发现了这个问题),虽然我没有答案,但我想我会分享我的想法。

  • 建设者的理想'应该只设置对象的状态,即:几个:

this.member = member;

在我看来,这与国际奥委会,继承,测试很好地发挥,只是味道不错。

然而繁重,有时是需要所以我一直试图做的是:

  • 通行证在繁重。

这意味着抽象是初始化代码到其他类和传球,在这通常是可能的,如果繁重是不是真的你的对象的责任,这样做其实这refactors到更好的代码。

如果这是不可能的,你需要在使用前初始化你的类的状态,然后添加一个initialse方法。这确实增加了时间依赖到你的代码,但是这不一定尤其是在使用IoC容器时,坏事:

CarEngine需要DrivingAssistComputer,而DrivingAssistComputer需要做重初始化,即加载所有参数,天气条件检查,等等。另外需要注意的是,CarEngine不直接与DrivingAssistComputer互动,它只是需要它存在,在旁边做自己的事情。事实上,如果没有DrivingAssistComputer在后台执行任务(在某处更改某个状态),引擎可能无法正常工作。如果我们使用IoC的则有:

// Without initialise (i.e. initialisation done in computer constructor) 
public CarEngine(FuelInjectors injectors, DrivingAssistComputer computer) { 
    this.injectors = injectors; 
    // No need to reference computer as we dont really interact with it. 
} 

... 

所以我们在这里的是一个构造函数的参数标记computer为扶养但实际上没有使用它。因此,这是丑陋的,但让我们来添加一个初始化方法:

public CarEngine(FuelInjectors injectors, DrivingAssistComputer computer) { 
    this.injectors = injectors; 
    // This ofcourse could also be moved to CarEngine.Initialse 
    computer.Initialise(); 
} 

... 

还没一个有凝聚力的班,但至少我们知道,我们依赖电脑上,即使我们没有直接与它的构造之外的交互。

另一种选择ofcourse是有一个CarEngineFactory,做:

CarEngine CreateEngine(FuelInjectors injectors) { 
    new DrivingAssistComputer().Initialise(); 
    return new CarEngine(injectors); 
} 

... 

不过,我觉得工厂和IOC只是混淆矩阵,所以我会去的第二个选项。

很想听听这方面的一些想法。

编辑1: 我错过了上面的另一个选择是使用Initialise方法,但将此调用移动到IoC初始化模块。所以创建和初始化仍然有所封装。

+0

+1'传递重负荷' - 这对我来说很有意义 – 2014-01-26 03:35:46

相关问题