2009-02-03 29 views
68

Enum-değerinimi int olarak serileştirmek istiyorum, ancak sadece adı aldım.Bir enum değerini int olarak nasıl serileştiririm?

public class Request { 
    public RequestType request; 
} 

public enum RequestType 
{ 
    Booking = 1, 
    Confirmation = 2, 
    PreBooking = 4, 
    PreBookingConfirmation = 5, 
    BookingStatus = 6 
} 

Ve kod

Request req = new Request(); 
req.request = RequestType.Confirmation; 
XmlSerializer xml = new XmlSerializer(req.GetType()); 
StringWriter writer = new StringWriter(); 
xml.Serialize(writer, req); 
textBox1.Text = writer.ToString(); 

This answer (başka soruya) (sadece ben yanlış yapmıyorum emin olmak için): Burada

benim (örnek) sınıf ve enum olan Enemlerin varsayılan olarak seriye serileştirilmesi gerektiğini gösteriyor gibi görünüyor, ancak bunu yapmıyor gibi görünüyor. Her değerin üzerinde "[XmlEnum (" X ")]" özelliği koyarak değer olarak serialize mümkün olmuştur

<?xml version="1.0" encoding="utf-16"?> 
<Request xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema"> 
    <request>Confirmation</request> 
</Request> 

, ama bu sadece yanlış geliyor: İşte benim çıkıştır.

cevap

62

Çoğu zaman insanlar ints değil, isim ister. Bu amaçla bir şim mülk ekleyebilir misin?

[XmlIgnore] 
public MyEnum Foo {get;set;} 

[XmlElement("Foo")] 
[EditorBrowsable(EditorBrowsableState.Never), Browsable(false)] 
public int FooInt32 { 
    get {return (int)Foo;} 
    set {Foo = (MyEnum)value;} 
} 

Yoksa IXmlSerializable kullanabilirsiniz, ama bu çok iş olduğunu.

+0

Sadece net olarak - snippet'in yaptığı şey, MyEnum özelliğine sahip XmlSerializer - IGNORE. Ve MyEnum prop'ı Int32 değerine çeviren FooInt32 Özelliğini SERIALIZE. Bu sizin için mükemmel çalışacaktır. – Cheeso

+0

Bu, Enum'un 3. taraf kitaplıklarına başvururken iyi bir çözümdür. – CtrlDot

+0

Ayrıca FooInt32 özelliğinin Foo adı olarak serileştirildiği de not edilmelidir.Bu cevabı en çok beğeniyorum çünkü enuminizde düzinelerce değer varsa, bunu sadece bir kez yapmak zorundasınız. –

-1

System.Enum sınıfına bir bakın. Ayrıştırma yöntemi bir dizeyi veya int temsilini Enum nesnesine dönüştürür ve ToString yöntemi Enum nesnesini serileştirilebilen bir dizeye dönüştürür.

+3

ile değiştirilmiş olmasıdır. gerçek sorun olan serileştirme sırasında bu saydamın nasıl kullanılacağını ele almıyor. –

13

ilginç bir yol için aşağıda tam örnek konsol uygulaması programı DataContractSerializer kullanarak aradığınızı elde etmek bakınız: writeObject için çağrısından sonra aşağıdaki gibi request.txt ait

using System; 
using System.IO; 
using System.Runtime.Serialization; 

namespace ConsoleApplication1 
{ 
    [DataContract(Namespace="petermcg.wordpress.com")] 
    public class Request 
    { 
     [DataMember(EmitDefaultValue = false)] 
     public RequestType request; 
    } 

    [DataContract(Namespace = "petermcg.wordpress.com")] 
    public enum RequestType 
    { 
     [EnumMember(Value = "1")] 
     Booking = 1, 
     [EnumMember(Value = "2")] 
     Confirmation = 2, 
     [EnumMember(Value = "4")] 
     PreBooking = 4, 
     [EnumMember(Value = "5")] 
     PreBookingConfirmation = 5, 
     [EnumMember(Value = "6")] 
     BookingStatus = 6 
    } 

    class Program 
    { 
     static void Main(string[] args) 
     { 
      DataContractSerializer serializer = new DataContractSerializer(typeof(Request)); 

      // Create Request object 
      Request req = new Request(); 
      req.request = RequestType.Confirmation; 

      // Serialize to File 
      using (FileStream fileStream = new FileStream("request.txt", FileMode.Create)) 
      { 
       serializer.WriteObject(fileStream, req); 
      } 

      // Reset for testing 
      req = null; 

      // Deserialize from File 
      using (FileStream fileStream = new FileStream("request.txt", FileMode.Open)) 
      { 
       req = serializer.ReadObject(fileStream) as Request; 
      } 

      // Writes True 
      Console.WriteLine(req.request == RequestType.Confirmation); 
     } 
    } 
} 

içeriği vardır :

<Request xmlns="petermcg.wordpress.com" xmlns:i="http://www.w3.org/2001/XMLSchema-instance"> 
    <request>2</request> 
</Request> 

Sen DataContractSerializer için System.Runtime.Serialization.dll derlemesine gerekir.

Bu XML serialize
[Serializable] 
public enum EnumToSerialize 
{ 
    [XmlEnum("1")] 
    One = 1, 
    [XmlEnum("2")] 
    Two = 2 
} 

(üst sınıf CustomClass olduğunu söylemek) şöyle:

<CustomClass> 
    <EnumValue>2</EnumValue> 
</CustomClass> 
+0

Soru, [XmlEnum ("...")] kullanımının XmlSerializer [EnumMember ("...")] koduna eşdeğer olduğunu belirtiyor - dolayısıyla OP'nin zaten bilmediği bir şey eklediğinden emin değilim. –

+1

Ayrıca - DataContractSerializer özel üyeleri desteklediğinden, daha basit olan yaklaşım, int ve enum arasında değişen bir * private * shim özelliği olur. –

+0

Evet, şunu gördüm: XmlEnum teşekkürler ama söylediğim gibi, bu sorunun ilginç bir çözümü olduğunu düşünüyorum. Hangi çözümün 'basit' subjektif ve nihayetinde bu soruya kesinlikle yanıt vericidir. Anlaşıldı: 'shim' yaklaşımı ile DataContractSerializer ve özel üyeler için destek yolu gitmek için yoldur. –

125

kolay yolu şöyle bağlıyor [XmlEnum] kullanmaktır Enum seçeneklerine açık sıralı olmayan değerler atamaktayım, bir seferde birden fazla değer belirtebileceğinizi kabul ediyorum (ikili bayraklar), kabul edilen cevap tek seçeneğinizdir. PreBooking'de Geçiş | PreBookingConfirmation, 9'un bir tamsayı değerine sahip olacak ve seri hale getirici, bir seri özelliği ile yayınlayarak, seri hale getiremeyecektir, ancak iyi çalışacaktır. Ya da belki de 3 değerini kaçırdınız :)

+0

Bunu daha az çalışma ve daha kolay okuma/anlama olarak tercih ediyorum. Bu yöntemin bir karşılaştırmasını görmek istiyorum ve yukarıdaki kabul edilen cevap –

+5

Bunun aslında kabul edilen cevaptan daha az mı olduğu tartışılabilir. Daha fazla değer değerleri = daha fazla bakım. – youwhut

+2

+1 Bu da benim tercih ettiğim yöntemdir - birkaç ekstra yönerge Enum'u doğru şekilde seri hale getirmenize izin verirken neden gereksiz bir şim özelliği yaratır. – CJM

0

Senden beri

+2

Sadece [Flags] adlı kullanışlı bir enum arkadaş buldum, bu da bit bayraklarını kullanmanıza ve doğru seçeneklere geri serileştirmelerine olanak tanıyor ... –

1
using System.Xml.Serialization; 

public class Request 
{  
    [XmlIgnore()] 
    public RequestType request; 

    public int RequestTypeValue 
    { 
     get 
     { 
     return (int)request; 
     } 
     set 
     { 
     request=(RequestType)value; 
     } 
    } 
} 

public enum RequestType 
{ 
    Booking = 1, 
    Confirmation = 2, 
    PreBooking = 4, 
    PreBookingConfirmation = 5, 
    BookingStatus = 6 
} 

Yukarıdaki yaklaşım benim için çalıştı.

İlgili konular