[英]Design class to hold multiple instances of other classes
你如何设计一个可以容纳其他类的实例的 class。 我会尽力解释。 每个新客户的Customer
class 实例。 客户购买汽车,然后对每辆汽车进行特定操作。 例如,
Customer c = new Customer();
// customer buys cars
c.buyMercedes();
c.buyBMW();
// operations done on the car
c.changeMercedesColor();
c.changeBMWtyres();
我可以做这样的事情:
Customer c = new Customer();
c.buy(Mercedes);
c.buy(BMW);
c.car("Mercedes").changeColor();
c.car("BMW").changetyres();
没有特定于任何汽车的操作。 我在想也许有一种方法可以在调用buy()
方法时实例化Car
class 。 为此设计 class 的正确方法是什么? 如果有不同的方式我应该 go 关于这个,请告诉我。
最简单的方法是为不同类型的汽车创建一个基础 class。 您所有的特定汽车(梅赛德斯、宝马)都将由此衍生。 通过使用通用基础 class 或接口,您的客户 class 可以对特定汽车进行操作,而无需具体了解它们。
public abstract class CarBase
{
private string _color;
public virtual void ChangeTires()
{
// do the default change tires
}
public virtual void ChangeColor(string _color)
{
_color = color;
}
}
然后,您可以创建特定类型的汽车:
public class Mercedes : CarBase
{
public override void ChangeColor(string color)
{
}
}
因为 CarBase 中的每个方法都是虚拟的,所以如果需要,每个特定的实现都可以提供自己的实现,否则它只依赖“默认”ChangeTires()。
例如,也许对于梅赛德斯来说,改变颜色意味着你必须得到特殊的轮胎。
public class Mercedes : CarBase
{
public override void ChangeColor(string color)
{
if (color == red)
AddRacingTires();
}
}
然后,您可以为客户提供添加新车辆的方法。
public class Customer
{
public Dictionary<string, CarBase> OwnedCars { get; set; }
public void BuyCar(string manufacture)
{
if (manufacture== "Mercedes")
OwnedCars[manufactor] = new Mercedes();
if (manufacture== "BMW")
OwnedCars[manufactor] = new BMW();
}
}
然后,您可以执行以下操作:
Customer c = new Customer();
c.BuyCar("Mercedes");
c.OwnedCars["Mercedes"].ChangeTires();
有更好的方法来管理汽车。 您可能想看看制造汽车的工厂: http://www.dofactory.com/Patterns/PatternFactory.aspx
您可能也不想要制造商词典(我想您会通过 VIN 或其他东西来引用它们)。 您也不想要像“Mercedes”这样的魔术字符串,因为您可能会在某处输入错误。 但这是可能效果最好的基本设计模式。
你想要作曲。 您可以拥有Car
的通用列表并从那里访问它们。
如果没有特定于任何特定汽车的操作,那么您只需将“制造”和/或“型号”作为汽车的属性。
第二种形式无疑优于第一种形式。
由于汽车可以独立于其所有者而存在,因此您应该能够在没有客户的情况下实例化汽车。 也许您可以向客户添加操作以添加新车并获取现有汽车。 您可能还希望通过 VIN 而不是制造来获得汽车。 任何一位客户都可能拥有不止一辆宝马。
changeColor 和 changeTyres 方法应该存在于您的 Car object 而不是您的客户 object 上。
Car bmw = carFactory.create("BMW");
customer.add(bmw);
Car bmwAgain = customer.get(bmw.Vin);
bmwAgain.changeColor("black");
由于您没有特定于任何汽车的操作,因此您不需要从 Car 派生。 假设您有一个Car
class 具有Brand
属性,这是一个枚举。 然后您可以像这样设计您的客户 class:
Customer c = new Customer();
c.buy(Brands.Mercedes);
c.buy(Brands.BMW);
buy
方法将创建一个Car
的新实例,设置它的Brand
属性并将其添加到cars
,这是一个List<Car>
类型的Customer
的实例变量。
如果您确定客户只能拥有一个品牌的汽车(没有客户拥有两辆梅赛德斯?也许是周末的 SLK 和在城市寻找停车位的 A?),那么您可以像这样定义您的界面:
c.getCar(Brands.Mercedes).changeColor();
c.getCar(Brands.BMW).changeTyres();
否则,我会公开汽车枚举并使用 LINQ:
var mercedeses = c.Cars.Where(car => car.Brand == Brands.Mercedes);
foreach (var car in mercedeces) {
car.changeTyres();
}
Inheritance 工厂就是您所需要的。
好的,这听起来有点像家庭作业,但是:
如果您要购买的所有物品都是汽车,那么诸如“服务”,“汽车”,“灯”,“轮胎”,“排气”,“油漆”之类的共同点也是您将要“改变”的物品
你可以有一个 BaseCar 的基础 class,然后你从它下来得到你的 BWM/Merc 等。
对于每个客户,您将拥有一个 class,您可以在其中将要购买的物品定义为基础汽车,但您可以向他们发送“new Mercedes()”并获得他们购买的实际汽车的新实例。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.