Подтвердить что ты не робот

Как я могу управлять частью XML-сериализации <? Xml?> С помощью .NET?

Я использую этот метод для сериализации моего объекта:

public static string XmlSerialize(object o)
{
    var stringWriter = new StringWriter();
    var xmlSerializer = new XmlSerializer(o.GetType());
    xmlSerializer.Serialize(stringWriter, o);
    string xml = stringWriter.ToString();
    stringWriter.Close();
    return xml;
}

Это делает XML, который начинается следующим образом:

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

Но я хочу, чтобы это выглядело так:

<?xml version = "1.0" encoding="Windows-1252" standalone="yes"?>
<MyObject xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">

Итак, как мне изменить кодировку на Windows-1252 и установить standalone = yes? Кроме того, как мне получить объект, чтобы исключить значение xmlns?

Я видел пару подобных вопросов, например этот, но я надеялся, что это может быть проще для меня, может быть, где-то установить некоторые атрибуты?

Обновление 2: посмотрев на ответ Джона и комментарии, и подумав об этом больше, я решил просто сделать второй метод. Я не думаю, что создание этого дурацкого пользовательского xml только для третьей стороны в одно время должно быть названо чем-то общим как "XmlSerialize" в первую очередь.

Итак, я создал второй метод, который принимает XML-документ и, во-первых, удаляет один элемент пространства имен следующим образом:

xElement.Attributes().Where(a => a.IsNamespaceDeclaration && a.Value == "http://www.w3.org/2001/XMLSchema").Remove();

тогда он записывает его в XML с кодом Джона. Наконец, он возвращает этот xml, следуя следующему выводу:

new XDeclaration("1.0", "Windows-1252", "yes").ToString()

И это некрасиво, но это дает мне именно то, что мне нужно для этой третьей стороны, чтобы понять мой XML.

4b9b3361

Ответ 1

Попробуйте следующее:

public static string XmlSerialize(object o)
{
    using (var stringWriter = new StringWriter())
    {
        var settings = new XmlWriterSettings
                           {
                               Encoding = Encoding.GetEncoding(1252),
                               OmitXmlDeclaration = true
                           };
        using (var writer = XmlWriter.Create(stringWriter, settings))
        {
            var xmlSerializer = new XmlSerializer(o.GetType());
            xmlSerializer.Serialize(writer, o);
        }
        return stringWriter.ToString();
    }
}

Это не избавится от пространства имен xsd:, но почему, почему вы хотите?


Обновление: Кажется, что всякий раз, когда вы используете StringWriter, вы получаете UTF-16, даже если вы используете XmlWriter поверх него с набором кодировок. Следующим шагом будет запись в MemoryStream. Но это ставит вопрос о том, почему вы хотите вернуть строку. Например, если вы собираетесь просто развернуться и вывести строку в поток, то мы должны напрямую выводить этот поток. То же самое для TextWriter.

Ответ 2

Вместо StringWriter вы можете использовать XmlTextWriter. Вот выдержка из моего кода с вашим набором кодировок.

XmlTextWriter textWriter = new XmlTextWriter(stream, Encoding.GetEncoding(1252));
textWriter.Namespaces = false;

Ответ 3

FWIW, я получил кодировку для работы с помощью XmlWriter с XMLWriterSettings. Вот пример:

...  
// My object type was from a class generated by xsd.  
XmlSerializer xms = new XmlSerializer(typeof(SomeType));  
SomeType objSt;
using(FileStream fs = new FileStream("C:\SomeFile.xml", FileMode.Open, FileAccess.Read))
{    
  using(XmlReader xr = XmlReader.Create(fs))  // Supposed to preserve encoding.  
  {  
    objSt = (SomeType)xms.Deserialize(xr);  
  }    
}  

...  
...  // Do some stuff, change some attribute values.  
...  

XmlWriterSettings xsw= new XmlWriterSettings();  
xsw.Indent= true;  
xsw.NewLineOnAttributes= true;  
xsw.Encoding = Encoding.GetEncoding(1252);  
using(XmlWriter xwXsw = XmlWriter.Create("C:\SomeFile_Changed.xml",xsw))
{    
  xms.Serialize(xwXsw, objSt);  
}  
...  
...  // Finish up and get out.
...  

По какой-то причине я смог заставить все это работать, просто используя объект XmlSerializer и сериализуя его с помощью TextWriter, поскольку в соответствии с MS help для XmlSerializer.Deserialize(XmlReader) "XmlReader автоматически обнаруживает и использует указанную кодировку по XML-документу". Затем я начал играть с XmlWriterSettings и сломал что-то....