使用附加方法在构造函数中进行虚拟调用
Virtual call in constructor with additional method
我遇到了一个问题,我需要在我的抽象 class' 构造函数中调用虚函数。
internal abstract class Item
{
protected Item(...)
{
...
CreateBuyButton(...);
}
protected abstract void CreateBuyButton(...);
}
如果我有这样的代码,resharper 会通知我这个问题,但是如果我将调用重构为另一个方法,resharper 似乎不会将此视为问题,我不确定这是否是一个问题与否。
internal abstract class Item
{
protected Item(...)
{
...
GetValue(...);
}
protected abstract void CreateBuyButton(...);
private void GetValue(...)
{
CreateBuyButton(...);
}
}
这有效吗?问题还会存在吗?
是的,可能还是有问题
当基础 class 运行 的构造函数时,派生 class 的构造函数还没有 运行。如果覆盖的方法包含依赖于派生的 class' 状态的逻辑,它可能会遇到问题,因为状态尚未初始化。
您可以通过从构造函数中删除逻辑并改用惰性初始化来避免该问题,例如
abstract class Item
{
private Button _buyButton = null;
public Item()
{
//Do nothing
}
public Button BuyButton
{
get
{
if (_buyButton == null) CreateBuyButton(); //Lazy initialization
return _buyButton;
}
}
public abstract void CreateBuyButton();
}
如果你需要传递一些状态,你必须存储它:
abstract class Item
{
private string _productName;
private Button _buyButton = null;
public Item(string productName)
{
_productName = productName;
}
public Button BuyButton
{
get
{
if (_buyButton == null) CreateBuyButton(_productName); //Lazy initialization
return _buyButton;
}
}
public abstract void CreateBuyButton(string caption);
}
我遇到了一个问题,我需要在我的抽象 class' 构造函数中调用虚函数。
internal abstract class Item
{
protected Item(...)
{
...
CreateBuyButton(...);
}
protected abstract void CreateBuyButton(...);
}
如果我有这样的代码,resharper 会通知我这个问题,但是如果我将调用重构为另一个方法,resharper 似乎不会将此视为问题,我不确定这是否是一个问题与否。
internal abstract class Item
{
protected Item(...)
{
...
GetValue(...);
}
protected abstract void CreateBuyButton(...);
private void GetValue(...)
{
CreateBuyButton(...);
}
}
这有效吗?问题还会存在吗?
是的,可能还是有问题
当基础 class 运行 的构造函数时,派生 class 的构造函数还没有 运行。如果覆盖的方法包含依赖于派生的 class' 状态的逻辑,它可能会遇到问题,因为状态尚未初始化。
您可以通过从构造函数中删除逻辑并改用惰性初始化来避免该问题,例如
abstract class Item
{
private Button _buyButton = null;
public Item()
{
//Do nothing
}
public Button BuyButton
{
get
{
if (_buyButton == null) CreateBuyButton(); //Lazy initialization
return _buyButton;
}
}
public abstract void CreateBuyButton();
}
如果你需要传递一些状态,你必须存储它:
abstract class Item
{
private string _productName;
private Button _buyButton = null;
public Item(string productName)
{
_productName = productName;
}
public Button BuyButton
{
get
{
if (_buyButton == null) CreateBuyButton(_productName); //Lazy initialization
return _buyButton;
}
}
public abstract void CreateBuyButton(string caption);
}