Я получаю нечетный результат при сериализации использования поля DateTime XmlSerializer.
У меня есть следующий класс:
public class RecordExample
{
[XmlElement("TheTime", DataType = "time")]
public DateTime TheTime { get; set; }
[XmlElement("TheDate", DataType = "date")]
public DateTime TheDate { get; set; }
public static bool Serialize(
Stream stream, object obj, Type objType, Encoding encoding)
{
try
{
var settings = new XmlWriterSettings { Encoding = encoding };
using (var writer = XmlWriter.Create(stream, settings))
{
var xmlSerializer = new XmlSerializer(objType);
if (writer != null) xmlSerializer.Serialize(writer, obj);
}
return true;
}
catch (Exception)
{
return false;
}
}
}
Когда я называю использование XmlSerializer со следующим кодом тестирования:
var obj = new RecordExample
{
TheDate = DateTime.Now.Date,
TheTime = new DateTime(0001, 1, 1, 12, 00, 00)
};
var ms = new MemoryStream();
RecordExample.Serialize(ms, obj, typeof(RecordExample), Encoding.UTF8);
txtSource2.Text = Encoding.UTF8.GetString(ms.ToArray());
Я получаю некоторые странные результаты, вот xml, который производится:
<?xml version="1.0" encoding="utf-8"?>
<RecordExample
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<TheTime>12:00:00.0000000+00:00</TheTime>
<TheDate>2010-03-08</TheDate>
</RecordExample>
Любая идея, как я могу заставить элемент "TheTime" содержать время, которое больше походит на это:
<TheTime>12:00:00.0Z</TheTime>
... поскольку это - то, что я ожидал?
Спасибо
Dave
посмотрите на этот вопрос Сериализация DateTime во время без миллисекунд и gmt
У меня самого были разные проблемы с этим ... однако я пытался сериализовать объект TimeSpan. Решение заключалось в том, чтобы иметь два свойства, одно из которых содержало TimeSpan, а другое - строковое представление TimeSpan, которое было сериализовано. Вот шаблон:
[XmlIgnore]
public TimeSpan ScheduledTime
{
get;
set;
}
[XmlElement("ScheduledTime", DataType="duration")]
public string XmlScheduledTime
{
get { return XmlConvert.ToString(ScheduledTime); }
set { ScheduledTime = XmlConvert.ToTimeSpan(value); }
}
Однако в этом коде время выводится в следующем формате:
<ScheduledTime>PT23H30M</ScheduledTime>
Определение продолжительности W3C здесь, которое объясняет это .
Расширяя комментарий, который я сделал к одному из других ответов.
public class RecordExample : IXmlSerializable
{
public DateTime TheTime { get; set; }
public DateTime TheDate { get; set; }
public XmlSchema GetSchema()
{
return null;
}
public void ReadXml(XmlReader reader)
{
// TODO : Deserialization logic here
}
public void WriteXml(XmlWriter writer)
{
writer.WriteElementString(
"date",
this.TheDate.ToString("yyyy-MM-dd"));
writer.WriteElementString(
"time",
this.TheTime.ToString("hh:mm:ss.fK"));
}
}
Сериализация следующим образом:
var rc = new RecordExample()
{
TheDate = DateTime.Today,
TheTime = DateTime.UtcNow
};
var serializer = new XmlSerializer(typeof(RecordExample));
var ms = new MemoryStream();
serializer.Serialize(ms, rc);
ms.Seek(0, SeekOrigin.Begin);
Console.WriteLine(new StreamReader(ms).ReadToEnd());
Пример вывода:
<?xml version="1.0"?>
<RecordExample>
<date>2010-03-08</date>
<time>04:26:16.1Z</time>
</RecordExample>
Я согласен с другими ответами (я еще не закончил писать, когда они появились). не похоже, что это возможно напрямую. Взгляд на источник с помощью Reflector показывает, что значение времени в конечном итоге преобразуется в строку с помощью System.Xml.XmlConvert.ToString, которая имеет жестко запрограммированный формат:
ЧЧ: мм: ss.fffffffzzzzzz
Таким образом, наличие двух свойств, реальное - [XmlIgnore] и строка, которую вы создаете самостоятельно, - хороший способ.