2009-01-26 16 views
5

Aşağıdaki kod için eşdeğer bir şey arıyorum, ancak her veri türü için bir anahtar deyimi kodlamak zorunda kalmadan herhangi bir değer türü için arıyorum. XmlConvert.ToString() öğesinin kabul ve nesne yükleyen bir aşırı yüklenme olmadığı için aşağıdaki kod derlenmiyor. Başka bir deyişleXmlConvert kullanarak bir dize bir dize olarak bir değer türünü nasıl dönüştürebilirim?

 int intValue = 10; 
     object boxedValue = (object)intValue; 
     string xmlValue = XmlConvert.ToString(boxedValue); 

, bundan daha iyi bir yol yoktur:

public static string ToXmlString(Type type, object value) { 

     switch(Type.GetTypeCode(type)) { 
      case TypeCode.Int32: 
       return XmlConvert.ToString((int) value); 
      case TypeCode.DateTime: 
       return XmlConvert.ToString((DateTime) value, XmlDateTimeSerializationMode.Unspecified); 
      case TypeCode.Boolean: 
       return XmlConvert.ToString((bool) value); 

      // TODO: Add case for all other value types! 

      default: 
       return value.ToString(); 
     } 
    } 

cevap

0

Sadece orada bu dışarı atmak için, XML'DE bir iş nesnesi dönüştürmek çalışıyorsunuz?

Belki de XmlSerialization'a bakmak isteyebilirsiniz. İş nesnesinde bazı öznitelikleri işaretlerseniz. Net sizin için tüm fantezi XML şeyler yapacak :).

Ayrıca, değerinizi kutlamanın bir nedeni var mı? XmlConvert.ToString(), birçoğu ilkel olan 19 aşırı yüklenmeye sahiptir.

+0

Başlarım için minnettarım ama XmlSerializer, DataContractSerializer cehennemden geçtim. XamlWriter ile oynadım bile. Değerlerim kutlanıyor, çünkü birçok veri türü ile ilgilenen bir Arabirim aracılığıyla onlara erişiyorum. –

2

Tüm değer türleri doğal olarak serileştirilebilir. Yani sadece bir XMLSerializer kullanmanız gerekiyor. Bu yapacağını gibi (senin yöntemine dayalı) şey:

public static string ToXmlString(Type type, object value) 
{ 
    StringBuilder sb = new StringBuilder(); 
    System.Xml.XmlWriter writer = System.Xml.XmlWriter.Create(sb); 
    System.Xml.Serialization.XmlSerializer serial = 
     new System.Xml.Serialization.XmlSerializer(type); 
    serial.Serialize(writer, value); 
} 
+0

Komik şey, XmlSerializer.Serialize içine izlemek için Reflector'ı kullanırsanız, sonunda, sonunda, yerel nesneyi nesneye döktükleri XmlConvert.ToString öğesini çağıran yöntemlere gönderilen büyük bir anahtar deyimine sahip olan SerializePrimitive adlı bir yönteme rastlarsınız. –

+0

Ama bu kötü bir şey mi? Tüm olan, anahtarın kodunuzdan çerçeve koduna taşınmasıdır. – DarkwingDuck

+1

ToXmlString (typeof (boolean), true) sonucu, "true" değerinden değil, true Lakedaimon

1

Başka bir seçenek daha sonra System.Xml.Linq.XContainer.GetStringValue bir kopyasını bakmak için yansıtıcı kullanmaktır

(o maalesef iç bulunuyor)
1

Yazmak istediğim bir serileştiricinin bir parçası olarak (zıt için birinden kaçınarak), zıt karşıt dönüşümü (türden dize) yapmam gerekiyordu. Deserialize ediyordum ve bu konu hakkında konuşmak için tek yazıydı, bu yüzden hala taze iken cevabımla güncelleniyorum.

Kullandığım yöntem, temel olarak ne yapmam gerektiğini öğrenmek için yansıma kullanmaktı. Aşağıdaki örnekte bulunan değişken türü, dönüştürdüğüm türün Type nesnesidir, E içeriği için hangi dönüştürücüyü dönüştüreceğimiz bir XmlNode ve newVar, döneceğimiz bir şablon T türünün bir örneğidir. Bu fragman ve nesneler/çeteleler farklı şekilde ele varsayar (orada hiçbir doğrudan dize atama/dökme neden olan) T üzerinde herhangi kısıtlamaları kabul etmez (nesneler ve çeteleler kırmak):

MethodInfo convertMethod; 

if(Type.GetTypeCode(type) != TypeCode.String) 
    convertMethod = typeof(XmlConvert).GetMethod ("To" + type.Name); 
else 
    convertMethod = E.InnerText.GetType().GetMethod("Clone"); 

if(convertMethod == null) 
{ 
    //Error 
} 
else 
{ 
    if(Type.GetTypeCode (type)!= TypeCode.String) 
     newVar = (T)convertMethod.Invoke(null, new object[] { E.InnerText }); 
    else 
     newVar = (T)convertMethod.Invoke (E.InnerText, new object[]{}); 
} 

(Dize işlenmesi gereken ToString() gibi özel bir durum olarak tamamen farklı bir şey yapar ve her şeyi bozar).

(orijinal yazı uyarınca) tersi (Ben serialize işlevini yazarsanız, güncelleyecektir test edilmemiş) gibi bir şey olacaktır:

MethodInfo convertMethod; 

if(Type.GetTypeCode(type) != TypeCode.String) 
    convertMethod = typeof(XmlConvert).GetMethod ("ToString", new Type[] {typeof(T)}); 
else 
    convertMethod = typeof(string).GetMethod("Clone"); 

if(convertMethod == null) 
{ 
    //Error 
} 
else 
{ 
    string str; 
    if(Type.GetTypeCode (type)!= TypeCode.String) 
     str = (string)convertMethod.Invoke(null, new object[] { Value }); 
    else 
     str = (string)convertMethod.Invoke (Value, new object[]{}); 
} 

Bu durumda, dönüşüm T den dize etmektir ve Değer, dönüştürdüğümüz bir T türü içerir. Aradaki fark, ToString'i istediğimiz, ancak T parametresinin bir parametresiyle fonksiyonu belirtmemizdir. Bu, yeterince benzersiz olmalıdır.