具有依赖项的数据对象

时间:2014-08-19 17:46:19

标签: c# design-patterns dependency-injection unity-container

我试图找到一个现有的问题,但我不确定如何简明扼要地陈述它。目前我有一组对象,每个对象都有一个Status对象。状态对象本身包含三种状态。原始状态从外部数据源读入,显示状态和输出状态。原始状态用于在外部查找以说明所显示状态应该是什么。显示的状态是用户可以更新的唯一状态。输出状态需要根据程序是否处于可视模式"或"非视觉模式"。我希望在显示状态更新时进行此更改。之前,项目状态未被抽象出来,一个项目只有一个州。然后我们发布处理项目并将其状态更改为所需的输出状态。这需要9秒多的时间来完成所有120000个项目并更新其输出状态。由于之前的重构,我现在已经抽象出显示和输出状态,并希望另外优化此输出状态转换。我当然想到在写出数据之前进行输出转换,但是有多个文件被写入数据,因此需要在多个地方进行这种转换。

示例:显示的状态正在更新为" Bad",因此,如果程序处于"可视模式",则输出状态需要更新为" Good" ;。但如果该节目处于"非视觉模式"然后它被设置为" Bad"。

所以我的问题是如何管理集合中数据对象所需的逻辑依赖性?我想过使用依赖注入,但我可能不得不手动而不是通过Unity的#34;魔法"此外,如果通过仅为其提供起始状态来构造新的Status对象,那么它似乎很麻烦。该集合位于一个主对象内部,因此我确实考虑过在那里管理集合的方法,但这似乎有点严格,更难以迭代并读取/更新Status对象。

以下是类结构的表示:

class MyMapObject
{
    // This will have 100000+ items
    public Dictionary<Coordinate,Item> MapCollection { get; set; }
    /*
        Various other properties and methods
        ...
    */
}

class Item
{
    public ItemStatus Status { get; set;}
    /*
        Various other properties and methods
        ...
    */
}

class ItemStatus
{
    public State OriginalState { get; private set; }

    public State OutputState { get; private set; }

    public State ShownState 
    {
        get { return _shownState; }
        set
        {
            _shownState = value;
            SetOutputState();
        }
    }

    private void SetOutputState()
    {
        case DieState.Bad:   // How do I inject visualInspectionMode?
            OutputState = visualInspectionMode ? DieState.Good : DieState.Bad;
            break;
        // other states ...
    }
}

1 个答案:

答案 0 :(得分:1)

  

状态对象本身包含三种状态。原始状态从外部数据源读入,当前状态和输出状态。

我们会考虑国家格局,所以这很令人不安。您将拥有状态对象,而不仅仅是enum属性。 Memento Pattern模式允许恢复到以前的状态,但至少我们正在查看某种链表结构。

CurrentState vs OutPutState听起来像是你两次定义同一个州。我最初的 guess 是我们想要构建一个CurrentState的状态对象,它将在&#34;输出状态中运行。方式。 I.E. OutputState应该是一种方法。

  

集合在一个主对象中,所以我确实想到了那里有管理集合的方法,但这似乎有点严格,更难以迭代并读取/更新Status对象。

如果您真的想控制集合,这实际上很好。这可以使您的对象看起来,感觉和行为像MasterObject而不是通用的.net集合对象。


  

我想过使用依赖注入,但我可能不得不手动而不是通过Unity的#34;魔法&#34;

每次对象更改状态时使用Unity容器?听起来像是超级矫枉过正。正如我从Dependency Injection in .NET

所理解的那样滥用DI容器概念
  

另外,如果通过赋予它一个起始状态来构造一个新的Status对象会很好看。

宾果!

  

该集合位于主对象内部,因此我确实想到了......

首先设计您的状态机,然后担心收集。

明确定义国家

Bad还是NotVisualMode?是Good还是VisualMode?首先,&#34;好&#34;并且&#34;坏&#34;没有任何意义。其次,你定义然后重新定义状态。它同样适用于CurrentStateOutputState

明确定义行动 - &gt;州过渡

  1. 因此应用程序变为可视会导致更改为Visual状态。
  2. 状态模式,一般

    1. 定义interface,为每个&#34;动作&#34;声明一种方法。导致状态改变
    2. 为每个州编写一个具体的类并实现该接口。
    3. 某事发生时,我们改变状态,我们创建一个新的状态对象。对象的方法根据它的状态运行。这就是所谓的OutputState可以做到的事情。
    4. &#34;操作&#34;导致状态改变。该应用程序来自&#34; visual&#34;到非视觉&#34;无论什么都可以被认为是同一件事。


        

      目前我有一组对象,每个对象都有一个Status对象。状态对象本身有三种状态。

      我怀疑这应该是一个单独的课程。状态对象不仅仅是一堆boolenum s,它也适用于给定状态。

      换句话说,您可能需要一个enum属性,表示我在StateOf.Confusion中,但它是该对象中的字段,属性和多态方法的总和是那个州。


      关于SOLID的想法

      - 界面隔离。我说状态模式interface将声明确定下一个状态的方法。我没有包含OutputState方法。

      OutputState和其他任何&#34;状态多态&#34;方法应在单独的interface或模板abstract类中声明。如果存在共同的处理结构,则abstract类将成为可行的方法。 See my answer to this question