Как я сериализую значение enum как int?
Я хочу сериализовать значение enum как int, но я получаю только имя.
Вот мой (пример) класс и перечисление:
public class Request {
public RequestType request;
}
public enum RequestType
{
Booking = 1,
Confirmation = 2,
PreBooking = 4,
PreBookingConfirmation = 5,
BookingStatus = 6
}
И код (чтобы быть уверенным, что я не ошибаюсь)
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();
Этот ответ (на другой вопрос), похоже, указывает, что перечисления должны быть сериализованы для ints по умолчанию, но, похоже, это не так. Вот мой вывод:
<?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>
Мне удалось сериализовать как значение, поместив атрибут "[XmlEnum (" X ")] на каждое значение, но это просто кажется неправильным.
Ответы
Ответ 1
В большинстве случаев людям нужны имена, а не ints. Вы можете добавить свойство прокладки для этой цели?
[XmlIgnore]
public MyEnum Foo {get;set;}
[XmlElement("Foo")]
[EditorBrowsable(EditorBrowsableState.Never), Browsable(false)]
public int FooInt32 {
get {return (int)Foo;}
set {Foo = (MyEnum)value;}
}
Или вы можете использовать IXmlSerializable
, но это очень много работы.
Ответ 2
Самый простой способ - использовать атрибут [XmlEnum] следующим образом:
[Serializable]
public enum EnumToSerialize
{
[XmlEnum("1")]
One = 1,
[XmlEnum("2")]
Two = 2
}
Это приведет к сериализации в XML (скажем, что родительский класс - CustomClass):
<CustomClass>
<EnumValue>2</EnumValue>
</CustomClass>
Ответ 3
Пожалуйста, ознакомьтесь с приведенной ниже программой Console Application для интересного способа достижения того, что вы ищете, с помощью DataContractSerializer:
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);
}
}
}
После вызова WriteObject содержимое request.txt выглядит следующим образом:
<Request xmlns="petermcg.wordpress.com" xmlns:i="http://www.w3.org/2001/XMLSchema-instance">
<request>2</request>
</Request>
Вам понадобится ссылка на сборку System.Runtime.Serialization.dll для DataContractSerializer.
Ответ 4
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
}
Этот подход работал у меня.
Ответ 5
Поскольку вы назначаете явные непоследовательные значения параметрам перечисления, я предполагаю, что вы хотите указать более одного значения за раз (двоичные флаги), тогда принятый ответ является вашим единственным вариантом. Прохождение в PreBooking | PreBookingConfirmation будет иметь целочисленное значение 9, и сериализатор не сможет десериализовать его, но его использование с помощью прокладки будет работать хорошо. Или, может быть, вы просто пропустили значение 3:)
Ответ 6
Взгляните на класс System.Enum. Метод Parse преобразует представление строки или int в объект Enum, а метод ToString преобразует объект Enum в строку, которая может быть сериализована.