2015-07-21 263 views
0

以下代码按原样工作,但我想在构造函数 中使用MyProperty类的引用,而不是内联代码中的强类型引用。c#将类参数传递给构造函数

如何做到这一点,我预计到裁判传递给myProperty的,但一切我曾尝试失败

我想PropertyClass能够处理任何myProperty的类即myProperty的任何引用在PropertyClass

如果我错过了显而易见的事物,仍然在学习如此抱歉!

任何帮助,非常感谢

萨拉

PropertyClass pc = new PropertyClass(!here!); // Would like to pass MyProperty class here 

pc.Settings.Add(new MyProperty("Fred", "Monday")); 
pc.SaveXml("MyTest.xml"); 




public class MyProperty 
{ 
    [XmlAttribute] 
    public string MyPropName { get; set; } 
    [XmlElement] 
    public string MyPropData { get; set; } 

    // default constructor needs to be parameterless for serialisation. 
    public MyProperty() 
    { 
    } 

    public MyProperty(string Name, string Data) 
    { 
     MyPropName = Name; 
     MyPropData = Data; 
    } 
} 



public class PropertyClass 
{ 
    public List<MyProperty> Settings { get; set; } 

    public PropertyClass()    // How to pass the required class here ? 
    {         // public PropertyClass(ref MyProperty myprop) 
     Settings = new List<MyProperty>(); 
    } 

    public void SaveXml(string fileName) 
    { 
     using (FileStream stream = new FileStream(fileName, FileMode.Create)) 
     { 
      XmlSerializer XML = new XmlSerializer(typeof(List<MyProperty>), new XmlRootAttribute("Settings")); 

      XmlSerializerNamespaces namespaces = new XmlSerializerNamespaces(); 
      namespaces.Add(string.Empty, string.Empty); 

      XML.Serialize(stream, Settings, namespaces); 
     } 
    } 
} 
+0

你试图通过只是你要存储的对象类型“PropertyClass”的实例?你有没有尝试过使用泛型?或者是泛型的序列化问题? –

+1

我想你正在寻找[泛型](https://msdn.microsoft.com/en-us/library/512aeb7t.aspx)?... –

+0

嗨很多感谢回复 - 我希望有一个密封的类,可以处理传递给它的任何'MyProperty'样式类。 MyProperty类可以包含任意数量的对象,并且提供的类的序列化是核心部分。总之,我只是不希望有一个PropertyClass的所有MyProperty要求,我也需要完全理解为什么我试图做的不工作! –

回答

2

我的PropertyClass的定义修改为

public class PropertyClass<T> 
{ 
    public List<T> Settings { get; set; } 

    public PropertyClass() 
    { 
     Settings = new List<T>(); 
    } 

    public void SaveXml(string fileName) 
    { 
     using (FileStream stream = new FileStream(fileName, FileMode.Create)) 
     { 
      XmlSerializer XML = new XmlSerializer(typeof(List<T>), new XmlRootAttribute("Settings")); 

      XmlSerializerNamespaces namespaces = new XmlSerializerNamespaces(); 
      namespaces.Add(string.Empty, string.Empty); 

      XML.Serialize(stream, Settings, namespaces); 
     } 
    } 
} 

type parameterT指定项目的类型在List<T>中,以便您可以实例化PropertyClass,如下所示

var pc = new PropertyClass<MyProperty>(); 

或者当您厌倦了MyProperty时,您可以将其更改为new PropertyClass<foo>(),而无需在其他地方更改它。

另一个不错的功能,我喜欢泛型是,你实际上可以把限制的类型参数的线,你声明它想:

public class PropertyClass<T> where T : MyClass, IMyInterface, new() 

这意味着T必须从MyClass衍生,它必须实现IMyInterface并且必须有一个无参数的构造函数。(显然你不需要添加所有这样的约束,但是在某些情况下它们都可以有用)。

我想多说一点,但我相信你可以玩它并找到它的一些用途。

+0

哇谢谢,这很快,我需要一点时间来吸收你说的话,但我想我明白你说的话(惊讶自己!),我真的不喜欢做我不懂的事情,我喜欢做5年后可以理解的整洁代码。顺便说一句,我正在从Forth转移到C#,所以没有任何意义上的壮举。非常感谢您的帮助。 –

+0

Namelesss一个感谢泛型实现了我所需要的,我已经标记了你的答案为接受。很多谢谢你的解释。 –

0

你这是怎么调用构造函数

PropertyClass pc = new PropertyClass(new MyProperty("Fred", "Monday")); 

这是构造

Public MyProperty MyProperty { get; set; } 
public PropertyClass(MyProperty _myProperty) 
{ 
    MyProperty = _myProperty 
} 
+1

你应该通过添加解释性的细节来改善这个答案的质量。所以对代码唯一的答案皱眉。 –

+0

@WilliamCustode它是代码,只是插入问题 – Paparazzi

0

您需要添加建筑物uctor采用一个MyProperty作为参数:

public PropertyClass(MyProperty myprop)    
{         
    Settings = new List<MyProperty> {myprop}; 
} 

注意MyProperty是引用类型所以ref是不必要这里(它已经的引用)。

+0

我已经尝试过,但如何剂量传递类的序列化拿起其参考。我觉得我在这里错过了一些重要的概念。我需要这个类能够处理许多不同的'MyProperty'类,它们将具有不同的配置。因此,如果我使用上面的方法,serialize类如何使用上述概念? –

1

我认为你需要一个通用的类。

public class PropertyClass<T> 
{ 
    public List<T> Settings { get; set; } 

    public PropertyClass() 
    { 
    Settings = new List<T>(); 
    } 
... 
} 

PropertyClass<MyProperty> pc = new PropertyClass<MyProperty>(); 

我必须补充说明你的命名很不清楚。 PropertyClass应该叫做XmlableList。而MyProperty已经存在,被称为NameValuePair<string,string>

+0

对不起,我试图让我做的事很简单,显然失败了,但我已经听取了你所说的话。很多谢谢 –

1

也许你正在寻找仿制药:

public class PropertyClass<TMyProperty> 
{ 
    public List<TMyProperty> Settings { get; set; } 

    public PropertyClass() 
    {         
     Settings = new List<TMyProperty>(); 
    } 
    .. 
} 
1

处理您的命名,PropertyClass实际上是一组属性;也许MyPropertyCollection会更好?

你在找什么叫做构造函数重载。基本上你再次指定构造,但这次参数:

public MyPropertyCollection() 
{ 
    Settings = new List<MyProperty>(); 
} 
public MyPropertyCollection(IEnumerable<MyProperty> collection) 
{ 
    Settings = new List<MyProperty>(collection); 
} 

或者允许var col = new MyPropertyCollection(new MyProperty(), new MyProperty(), new MyProperty())你可以这样做:

public MyPropertyCollection(params MyProperty[] collection) 
{ 
    Settings = new List<MyProperty>(collection); 
} 

虽然你应该小心的是,它并不感到右如果您稍后想要引入其他参数,那么它可能会失败。

而且,你基本上包裹的列表,你也可以考虑的是System.Collection.ObjectModel.Collection<T>类为基础:

// The Collection<MyProperty> base class is responsible for maintaining the list 
public class MyPropertyCollection : Collection<MyProperty> 
{ 
    public MyPropertyCollection() 
    { 
     // Default base() constructor is called automatically 
    } 

    public MyPropertyCollection(IList<MyProperty> properties) 
     : base(properties) 
    { 
     // Overloaded constructor calls base constructor with collection of properties 
    } 

    public void SaveXml(string fileName) 
    { 
     using (var stream = new FileStream(fileName, FileMode.Create)) 
     { 
      // Serializer should now target this very class 
      var xml = new XmlSerializer(typeof (this), new XmlRootAttribute("Settings")); 

      var namespaces = new XmlSerializerNamespaces(); 
      namespaces.Add(string.Empty, string.Empty); 

      xml.Serialize(stream, this, namespaces); 
     } 
    } 
} 
+0

对不起,它被称为MypropCollection,但由于我没有使用集合,我改变了它的名字来问这个问题。我真诚地感谢你的回复,现在需要消化你所说的话,我需要理解我为什么和我正在做什么,并且你可以猜测这是一个更大的项目的一小部分,之前的编码已经全部出现了所有这些都有所不同。赞赏莎拉 –

相关问题