如何在c#中拥有一种虚拟静态成员?
本文关键字:一种 虚拟 静态成员 拥有 | 更新日期: 2023-09-27 18:10:51
我有一个类:
public class Food
{
public static IList<Ingredient> ingredients
public bool uses(Ingredient i)
{
return ingredients.Contains(i);
}
}
然后我继承它做各种各样的食物,像:
public class Cake : public Food
{
public static IList<Ingredient> ingredients = new List<Ingredient>()
{
Sugar,
Eggs,
Milk
}
}
现在我希望能够执行
Food f = getFood();
if (f.uses(Eggs))
{
// Do something
}
所以我想有一个静态的成分列表,例如,所有蛋糕都可以共享,而不是每个蛋糕实例的列表,并能够以虚拟的方式访问它。
如果需要的话,我愿意搅动代码以获得类似的效果!在这种情况下,OOD"倾向于"使类Food
抽象,因为"成分"将不同于Food
到另一个。因此,正如其他人指出的那样,使这个列表static
是没有意义的,因为static
应该是一个属性的修饰符,该属性不受对象的区分。
我的建议如下:
public abstract class Food
{
public abstract IList<Ingredient> Ingredients
{
get;
}
}
现在任何类——具体的——将从Food
驱动,因此它必须实现这个属性,以便它给出自己的ingredients
:
public class Cake : Food
{
public override IList<Ingredient> Ingredients
{
get {
return new IList<Ingredient>()
{ Sugar, Eggs, Milk };
}
}
}
你可以定义一个方法GetIngredients()
让子类覆盖:
public abstract class Food
{
public static IList<Ingredient> ingredients
public bool uses(Ingredient i)
{
return GetIngredients().Contains(i);
}
protected abstract IList<Ingredient> GetIngredients();
}
public class Cake : public Food
{
public static IList<Ingredient> ingredients = new List<Ingredient>()
{
Sugar,
Eggs,
Milk
}
protected override IList<Ingredient> GetIngredients()
{
return ingredients ;
}
}
把所有这些实例都变成一个类怎么样?如:
class Food
{
public IList<Ingredient> ingredients;
public Food(IList<Ingredient> ingredients)
{
this.ingredients = ingredients.Clone();
}
public bool uses(Ingredient i)
{
return ingredients.Contains(i);
}
}
Food Cake = new Food({ Sugar, Eggs, Milk });
这些成分不需要是静态的。您可以从Cake类派生出所有类型的蛋糕,这样它们就继承了共同的成分:
public class Cake : Food
{
public IList<Ingredient> ingredients = new List<Ingredient>()
{
Sugar,
Eggs,
Milk
}
}
public class DevilsFoodCake : Cake
{
public DevilsFoodCake()
{
ingredients.AddRange(new List<Ingredient>()
{
Chocolate,
SourCream
}
}
}
如果您的目标是每个类型有一个成分集合,那么您就不能真正做到这一点。我认为你能做的最好的事情,虽然不是我不推荐的,是把负责任的移动到另一个类,像这样:
public class IngredientStore
{
public static IngredientStore Current
{
get;
private set;
}
private Dictionary<Type, List<Ingredient>> ingredients = new Dictionary<Type, List<Ingredient>>();
static IngredientStore()
{
Current = new IngredientStore();
}
public void Register(Type type, List<Ingredient> ingredients)
{
this.ingredients[type] = ingredients;
}
public bool Uses(Type type, Ingredient ingredient)
{
// TODO: check the type is registered
return this.ingredients[type].Contains(ingredient);
}
}
public class Food
{
public bool Uses(Ingredient ingredient)
{
return IngredientStore.Current.Uses(this.GetType(), ingredient);
}
}
public class Cake : Food
{
static Cake()
{
IngredientStore.Register(typeof(Cake), new List<Ingredient>
{
Ingredient.Butter,
Ingredient.Eggs,
Ingredient.Flour,
};
}
}
public class CherryCake : Cake
{
static CherryCake()
{
IngredientStore.Register(typeof(CherryCake), new List<Ingredient>
{
Ingredient.Butter,
Ingredient.Eggs,
Ingredient.Flour,
Ingredient.Cherries,
};
}
}