简体   繁体   English

抽象工厂模式

[英]Abstract factory pattern

I have a class, CMyDataClass , to store data, which has three member variables and two constructors like 我有一个类CMyDataClass来存储数据,它具有三个成员变量和两个构造函数,例如

public class CMyDataClass
{
    public String strIndex, strName;
    public int nType;
    public CMyDataClass()
    {
        strIndex = "";
        strName = "";
        nType = 0;
    }
    public CMyDataClass(String ind, String name, int ty)
    {
        strIndex = ind;
        strName = name;
        nType = ty;
    }
}

And in another class ( CMain ) I've a List<CMyDataClass> which contains two objects like 在另一个类( CMain )中,我有一个List<CMyDataClass> ,其中包含两个对象,例如

 List<CMyDataClass> lstMyDataList = new List<CMyDataClass> { new CMyDataClass("", "", 1), 
                                                             new CMyDataClass("", "", 2) };

I have two child classes which inherit the CMyDataClass and each contain a function to fill the data structure. 我有两个子类,它们继承了CMyDataClass ,每个子类都包含一个填充数据结构的函数。

The function in the child class will fill the object based on the ntype . 子类中的函数将基于ntype填充对象。

Here are my child classes 这是我的孩子班

//Class One

class COne : CMyDataClass
{
    public static bool FillData(CMyDataClass objCMDClass)
    {
        if (objCMDClass.nType == 1)
        {
            objCMDClass.strIndex = "Index-One";
            objCMDClass.strName = "One";
            return true;
        }
        return false;
    }
}



//Class Two

class CTwo : CMyDataClass
{
    public static bool FillData(CMyDataClass objCMDClass)
    {
        if (objCMDClass.nType == 2)
        {
            objCMDClass.strIndex = "Index-Two";
            objCMDClass.strName = "Two";
            return true;
        }
        return false;
    }
}

In the CMain class I execute the child class functions like CMain类中,我执行子类函数,例如

 public void Func()
    {
        for (int index = 0; index < lstMyDataList.Count; index++)
        {
            if (COne.FillData(lstMyDataList[index]) == false)
                if (CTwo.FillData(lstMyDataList[index]) == false)
                    MessageBox.Show("No data found");
        }
    }

Now the problem is: if COne or CTwo fills the data object, it return an object of type CMyDataClass . 现在的问题是:如果COneCTwo填充了数据对象,它将返回CMyDataClass类型的对象。 But I need the object of the child class ie, if COne fills the Object then the object should be of COne type, or if CTwo then the object should be CTwo object. 但是我需要子类的对象,即,如果COne填充了Object,则该对象应为COne类型,或者如果CTwo则该对象应为CTwo对象。

So I changed my Child class as 所以我改变了我的Child

class COne : CMyDataClass
  {
    public static bool FillData(CMyDataClass objCMDClass)
    {
        if (objCMDClass.nType == 1)
        {
            COne obj=new COne();
            obj.strIndex = "Index-One";
            obj.strName = "One";
            objCMDClass=obj
            return true;
        }
        return false;
    }
}

But this will not fill the object in the lstMyDataList , 'cause it creates a new object. 但这不会将对象填充到lstMyDataList ,因为它会创建一个新对象。

I can use type cast if my CMyDataClass is abstract. 如果我的CMyDataClass是抽象的,我可以使用type cast CMyDataClass But if I make it as abstract I can't fill the lstMyDataList as follows( object type unknown ). 但是,如果我将其抽象,则无法按如下方式填充lstMyDataList (对象类型unknown)。

 List<CMyDataClass> lstMyDataList = new List<CMyDataClass> { new CMyDataClass("", "", 1), new CMyDataClass("", "", 2) };

How to cast the object to child type,based on which class fills the object? 如何根据哪个类填充对象将对象转换为child类型?

Thanks in advancce. 谢谢。

You can't cast the objects to the child type, since it's not instance of the child type. 您不能将对象转换为子类型,因为它不是子类型的实例。 You're not using inheritance, you're creating instances of CMyDataClass , and initialize them differently, depending on a parameter. 您不使用继承,而是创建CMyDataClass实例,并根据参数以不同的方式初始化它们。

It's hard to tell what exactly you need or want, and, given that, it's unclear whether inheritance is needed here at all. 很难说出您到底需要什么或想要什么,并且鉴于这一点,目前还不清楚是否需要继承。 But if it's a factory you want, it could be something like this: 但是如果这是您想要的工厂,则可能是这样的:

    public class CMyDataClass
    {
        // ...snipped definition...
        public CMyDataClass(int type)
        {
            nType = type;
        }        

        public virtual void FillData()
        {
        }

        static public CMyDataClass Create(int type)
        {
            switch (type)
            {
                case 1:
                   return new COne(type);
                case 2:
                   return new CTwo(type);
                default:
                   return null // or throw an exception, whatever is appropriate
            }
        }
    }

    public class COne : CMyDataClass
    {
         public COne(int type)
             : base(type)
         {
         }

         public override void FillData()
         {
              strIndex = "Index-One";
              strName = "One";             
         } 
    }

    public class CTwo : CMyDataClass
    {
         public CTwo(int type)
             : base(type)
         {
         }

         public override void FillData()
         {
              strIndex = "Index-Two";
              strName = "Two";             
         } 
    }

//....
    List<CMyDataClass> lstMyDataList = new List<CMyDataClass> { CMyDataClass.Create(1), 
                                                                 CMyDataClass.Create(2) }
//....

//....
    public void Func()
    {
        for (int index = 0; index < lstMyDataList.Count; index++)
        {
            lstMyDataList[index].FillData();
        }
    }
//....

What about wrapping the CMyDataClass inside another class, and put instances of the new class inside the list box? 将CMyDataClass包装在另一个类中,然后将新类的实例放在列表框中,该怎么办? Then you can have instances of either COne or CTwo inside depending on which method was used to fill it. 然后,可以使用内部填充方法来填充COne或CTwo的实例。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM