【问题标题】:Enforcing Equality and Uniqueness Among Inherited Objects在继承对象之间强制平等和唯一
【发布时间】:2014-09-07 02:27:51
【问题描述】:

我有一个关于我的对象模型结构的一般性问题。也许我从错误的方向以隧道视野接近这个。我有两个类,Item 和 SerializedItem。我已经将它们定义为:

public class Item
{
    public string ItemNumber { get; set; }
    public string Description { get; set; }
    public double Cost { get; set; }
}

public class SerializedItem : Item
{
    public string SerialNumber { get; set; }
    public MyObject Location { get; set; }
}

商品是商品的通用定义,包含该商品的通用信息。 SerializedItem 是特定物理项目的表示。我的困难在于,任何时候只有一个具有特定 ItemNumber 的 Item 应该存在于内存中,我不确定在允许 SerializedItem 作为其基本类型的同时执行该约束的最佳模式。

也许这是更合适的方法?我没有太多使用“New”关键字的经验,而且我过去一直避免使用它,而是支持不需要使用它的继承结构。

public class Item
{
    public string ItemNumber { get; set; }
    public string Description { get; set; }
    public double Cost { get; set; }
}

public class SerializedItem : Item
{
    private Items _item;
    public SerializedItemz(Item item)
    {
        _item = item;
    }

    public new string ItemNumber
    {
        get { return _item.ItemNumber; }
        set { _item.ItemNumber = value; }
    }

    public new string Description
    {
        get { return _item.Description; }
        set { _item.Description = value; }
    }

    public new double Cost
    {
        get { return _item.Cost; }
        set { _item.Cost = value; }
    }

    public string SerialNumber { get; set; }
}

对于如何处理此问题的任何指导,我将不胜感激。我不拘泥于任何特定的解决方案。

为了清楚起见:

Item 类是特定产品“Widget A”的表示。它包含有关 Widget A 的成本、重量、尺寸等信息。无论生产多少个 Widget A,它们都共享此信息。

SerializedItem 类表示该产品线中的实际项目“Widget A 001”。它包含有关该物品的物理位置及其生产和销售历史的信息。

如果 Item 对象已更新,则所有 SerializedItems 都应反映该更改。

【问题讨论】:

  • 为什么你试图将Item设为基类型,而它的派生类型实际上不应该从它继承任何东西?
  • 也许这不是正确的方法。但是派生类型应该继承Item的所有属性和方法。
  • @Servy 请查看编辑。希望这能让我对我的目标有所了解。

标签: c# .net inheritance design-patterns


【解决方案1】:

我不确定在允许 SerializedItem 作为其基本类型的同时执行该约束的最佳模式

乍一看,轻量级工厂模式似乎很合适。创建一个类,其职责是创建Items,跟踪哪些已经创建,并确保只创建一个具有给定键的项目。

您还可以在工厂中构建逻辑以创建不同的子类型,例如SerializedItem - 您只需要提供适当的 SPI 来确定需要什么类型并收集必要的输入。

基本实现看起来像:

public static class ItemFactory
{
    public static Dictionary<string, Item> _Items = new Dictionary<string, Item>;

    public static Item GetItem(string itemNumber)
    {
        if(!_Items.ContainsKey(itemNumber))
        {
            _Items[itemNumber] = new Item(itemNumber);
            // Initialize item if necessary
        }

        return _Items[itemNumber];
    }
}

SerializedItem 类是该产品线中实际项目的表示

一个合适的设计是将Item 变成ItemType 并使用composition 而不是inheritance。因此,您的第二种方法(SerializedItem 不会从 Item 继承的更改)看起来是有效的。

【讨论】:

  • 工厂模式是我目前用来强制唯一性的东西,并且几乎完全按照描述的方式实现。我想很可能是我在这里想多了,试图解决一个不一定存在的问题。
  • @Michael - 不一定 - 享元模式有很多优点 - 听起来你只需要打破继承部分并改为使用组合(基本上与没有继承的情况相同)和newing 属性)。
  • 我最初的想法是支持多态行为。在这种情况下,接口可能是更合适的解决方案?在将对象作为接口进行操作时,两者都实现了 IItem 并且可能覆盖了相等性?
【解决方案2】:

如果 Item 确实是一个未实例化的基类,则将其标记为抽象并通过您的具体 SerializedItem 类(以及您可能拥有的任何其他派生类)工作。如果您只希望内存中具有给定项目编号的单个项目,那么您可以考虑在项目编号上索引的 Dictionary 类型集合。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2021-08-25
    • 2017-04-20
    • 1970-01-01
    • 2019-12-06
    • 1970-01-01
    • 2021-03-25
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多