0

同じ構造を持つ 2 つのクラス ツリーがあります。ある構造体の新しいクラス オブジェクトを、その型から作成し、他の構造体の対応するクラスの属性を使用して作成したいと考えています。

ここで私の制御構造のクラス:

public class ControlBase
{
    public ControlBase(string name);
    string name;
}
public class ControlA : ControlBase
{
    public ControlA(string name, int val) : base(name);
    int val;
}
public class ControlB : ControlBase
{
    public ControlB(string name, double val) : base(name);
    double val;
}

xml データ項目クラス:

public class XMLBase
{
    string name;
}
public class XMLA : XMLBase
{
     int val;
}
public class XMLB : XMLBase
{
     double val;
}

xml 構造からのオブジェクトのリストがありますが、問題は次のとおりです。制御構造からオブジェクトの同等のリストを作成するにはどうすればよいですか。

私はこのようなことができることを知っていますが、それがきれいな解決策だとは思いません。

foreach (XMLBase xmlItem in xmlList)
{
    if(xmlItem is XMLA)
    {
         XMLA toAdd = (XMLA)xmlItem;
         controlList.Add(new ControlA(toAdd.name, toAdd.val));
    }
    if(xmlItem is XMLB)
    ...
}

編集:私が忘れたいくつかの制約

  1. XML オブジェクトは生成されたコードであるため、触れないでください。
  2. 複数の値メンバーを持つことができます
4

3 に答える 3

1

この方法を試してください。階層をクライアントから切断したままにし、オブジェクトの動作方法がわかっている場所でオブジェクトのコピーを制御します。

public abstract class ControlBase
{
    protected ControlBase() { }      

    public ControlBase(string name)
    {
        this.name = name;
    }

    public abstract string DisplayMe();        

    protected string name;
}


public class ControlA : ControlBase
{
    public ControlA() { }

    public ControlA(string name, int val) : base(name) { this.val = val; }

    int val;

    public override string DisplayMe()
    {
        return val.ToString();
    }
}

public class ControlB : ControlBase
{
    public ControlB(string name, double val) : base(name) { this.val = val; }

    double val;

    public override string DisplayMe()
    {
        return val.ToString();
    } 
}



public abstract class XMLBase
{
    public string Name {get; set;}

    public abstract ControlBase ToControl();

}

public class XMLA : XMLBase
{
    public override ControlBase ToControl()
    {
        return new ControlA(Name, Val);
    }

    public int Val {get; set;}
}

public class XMLB : XMLBase
{       
    public override ControlBase ToControl()
    {
        return new ControlB(Name, Val);
    }

    public double Val {get; set;}
}


public class Client
{
    public static void Run()
    {
        IList<XMLBase> xmlList = new List<XMLBase>();

        xmlList.Add(new XMLA() { Name = "minion1", Val = 1 });
        xmlList.Add(new XMLB() { Name = "minion2", Val = 1.232323 });

        IList<ControlBase> controls = new List<ControlBase>();
        foreach (var xmlItem in xmlList)
        {
            var ctrl = xmlItem.ToControl();
            controls.Add(ctrl);
        }


        foreach (ControlBase ctrlBase in controls)
        {
            Console.Out.WriteLine(ctrlBase.DisplayMe());
        }
    }
}
于 2014-02-06T11:00:00.507 に答える
0

XML クラスを変更できる場合は、仮想メソッドを追加してみませんか。

public virtal ControlBase ToControl();

次に、各 XML クラスにそれを実装させます。

public class XMLBase
{
    string name;

    public virtual ControlBase ToControl()
    {
       return new ControlBase(name);
    }
}
public class XMLA : XMLBase
{
    int val;

    public override ControlBase ToControl()
    {
       return new ControlA(name, val);
    }
}
public class XMLB : XMLBase
{
    double val;

    public override ControlBase ToControl()
    {
       return new ControlB(name, val);
    }
}

ループは次のようになります。

foreach (XMLBase xmlItem in xmlList)
{
  var control = xmlItem.ToControl();
  controlList.Add(control);
}

Controlこれには、作成方法を知っているもののすぐ隣に作成を配置するという利点があります。

抽象化できる場合は、XMLBase抽象化もできるため、これはより良いでしょうToControl。このようにして、派生クラスは、オーバーライドすることを覚えておく必要がなく、強制的に実装されます。

于 2014-02-06T11:12:50.233 に答える