XML десериализация «стандартизация» окончания строк, как это остановить? (.СЕТЬ) - PullRequest
9 голосов
/ 12 июля 2009

У меня есть класс со свойством, помеченным [XmlText], который принимает многострочный ввод. В моем XML-файле я проверил, что окончания строк в текстовом содержимом являются такими же "\r\n", как и остальная часть файла.

Код, который я использую для десериализации:

XmlSerializer configSerializer = new XmlSerializer(typeof(WorldList));
string file = "test.xml";

if (File.Exists(file))
{
    using (TextReader r = new StreamReader(file))
    {
        foo = configSerializer.Deserialize(r);
    }
}

Но внутри установщика свойства [XmlText], value уже имеет "\n" в качестве окончания строки. Основная причина этого раздражает, потому что "\n" окончания строки не отображаются должным образом в TextBox ... Я не совсем уверен, какая часть вызывает проблемы, но я думал, что кто-то здесь может пролить осветить ситуацию.

Ответы [ 2 ]

11 голосов
/ 12 июля 2009

Я изменил пример кода, чтобы было проще быстро поместить код в среду разработки C #. Я также намеренно не включил использование операторов - это только пример кода.

Для примера у нас есть следующий класс, который мы хотим сериализовать:

   public class DataToSerialize
   {
       public string Name { get; set; }
   }

Если мы попытаемся сериализовать и десериализовать это так, как вы описываете строку, где выводится «Same», то не будет выполняться (я предполагаю, что код будет работать в Windows с Environment.NewLine, замените на «\ r \ n "если вы не):

    DataToSerialize test = new DataToSerialize();
    test.Name = "TestData" + Environment.NewLine;
    XmlSerializer configSerializer = new XmlSerializer(typeof(DataToSerialize));
    MemoryStream ms = new MemoryStream();
    StreamWriter sw = new StreamWriter(ms);
    configSerializer.Serialize(sw, test);
    ms.Position = 0;
    DataToSerialize deserialized = (DataToSerialize)configSerializer.Deserialize(ms);
    if (deserialized.Name.Equals("TestData" + Environment.NewLine))
    {
        Console.WriteLine("Same");
    }

Однако это можно исправить, вручную назначив сериализатору XmlTextReader с его свойством Normalization, установленным в false (свойство, используемое по умолчанию в сериализаторе, установлено в true):

    DataToSerialize test = new DataToSerialize();
    test.Name = "TestData" + Environment.NewLine;
    XmlSerializer configSerializer = new XmlSerializer(typeof(DataToSerialize));
    MemoryStream ms = new MemoryStream();
    StreamWriter sw = new StreamWriter(ms);

    configSerializer.Serialize(sw, test);
    ms.Position = 0;
    XmlTextReader reader = new XmlTextReader(ms);
    reader.Normalization = false;
    DataToSerialize deserialized = (DataToSerialize)configSerializer.Deserialize(reader);
    if (deserialized.Name.Equals("TestData" + Environment.NewLine))
    {
        Console.WriteLine("Same");
    }

То же самое теперь будет распечатывать, что, если я не ошибаюсь, то поведение, которое вам требуется?

4 голосов
/ 12 июля 2009

Если бы вы сериализовали , то XmlWriterSettings.NewLineHandling (Replace) стоило бы попробовать - но это не поможет чтению. Немного шероховатый, но, возможно, сделайте это прямо в сеттере:

private string text;
[XmlText]
public string Text {
    get { return text; }
    set 
    {
        Regex r = new Regex("(?<!\r)\n");
        text = r.Replace(value, "\r\n"); 
    }
}
...