Re: Баг в XmlSerializer.Deserialize...
От: MatFiz Россия  
Дата: 03.02.06 06:47
Оценка: 60 (8)
Здравствуйте, VVitaliy, Вы писали:

VV>Обаружил противный баг в методе XmlSerializer.Deserialize.

VV>Суть:
VV>Если сериализован класс со строковыми полями содержащими escapе characters like \r\n\t то сериализуются они нормально, при десериализации вычитываются в поток тоже нормально, но как только мы делаем Deserialize для объекта то в стоковые поля попают с строки с искаженными последовательностями таких символов. Наблюдаются разные искажения но чаще всего исчезает символ \r или он же заменяется на \t.

VV>Была мысль поотлаживать создаваемый слр код десериализатора, а смысл,

VV>потеряю времени день два, может даже найду баг, а чего дальше с этим делать, собственный десериализатор для нескольких десятков классов как-то не вписывается в проект по срокам...

VV>Это критичная часть проекта, и как обойти не представляю, вынимать строки через regexp... бред.


VV>Есть у кого какие мнения по данному поводу?


Вот код:

Program.cs
using System;
using System.Collections.Generic;
using System.Windows.Forms;
using System.Xml.Serialization;
using System.Xml;
using System.Text;
using System.IO;

namespace XmlSerialization
{
    static class Program
    {
        /// <summary>
        /// The main entry point for the application.
        /// </summary>
        [STAThread]
        static void Main()
        {
            string param = "a\rb\nc\td";
            Class1 class1 = new Class1(param, param);

            XmlSerializer ser = new XmlSerializer(typeof(Class1));
            StringBuilder sb = new StringBuilder();
            StringWriter sw = new StringWriter(sb);

            XmlWriterSettings xws = new XmlWriterSettings();  // Смотри сюда
            xws.NewLineHandling = NewLineHandling.Entitize;   // Особенно сюда
            xws.Indent = true;
            XmlWriter xw = XmlTextWriter.Create(sw, xws);
            ser.Serialize(xw, class1);

            string serializedObject = sb.ToString();
            Console.WriteLine(serializedObject);

            StringReader sr = new StringReader(serializedObject);
            Class1 deserCalss1 = (Class1)ser.Deserialize(sr);

            Console.WriteLine(string.Format("Original == deserialized is {0}", class1 == deserCalss1));

            Console.WriteLine("Press any key to exit");
            Console.ReadKey();
        }
    }
}


Class1.cs
using System;
using System.Collections.Generic;
using System.Text;
using System.Xml.Serialization;

namespace XmlSerialization
{
    public class Class1
    {
        public Class1()
        {
        }

        public Class1(string name1, string name2)
        {
            _name1 = name1;
            _name2 = name2;
        }

        private string _name1;
        private string _name2;

        [XmlAttribute]
        public string Name1
        {
            get { return _name1; }
            set { _name1 = value; }
        }

        [XmlElement]
        public string Name2
        {
            get { return _name2; }
            set { _name2 = value; }
        }

        public static bool operator ==(Class1 c1, Class1 c2)
        {
            return (c1._name1 == c2.Name1 && c1._name2 == c2.Name2);
        }

        public static bool operator !=(Class1 c1, Class1 c2)
        {
            return !(c1 == c2);
        }
    }
}


Смотри комментарии в коде.
How are YOU doin'?
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.