使用C#中的德语小数分隔符对XML进行XML反序列化

时间:2011-12-11 11:50:12

标签: c# xml serialization localization xml-deserialization

我正在尝试从“德语”xml字符串反序列化Movie对象:

string inputString = "<?xml version=\"1.0\"?>"
    + "<movie title=\"Great Bollywood Stuff\">"
    + "<rating>5</rating>"
    + "<price>1,99</price>" // <-- Price with German decimal separator!
    + "</movie>";

XmlSerializer movieSerializer = new XmlSerializer(typeof(Movie));
Movie inputMovie;

using (StringReader sr = new StringReader(inputString))
{
    inputMovie = (Movie)movieSerializer.Deserialize(sr);
}
System.Console.WriteLine(inputMovie);

这里是Movie类供参考:

[XmlRoot("movie")]
public class Movie
{

    [XmlAttribute("title")]
    public string Title { get; set; }

    [XmlElement("rating")]
    public int Rating { get; set; }

    [XmlElement("price")]
    public double Price { get; set; }

    public Movie()
    {

    }

    public Movie(string title, int rating, double price)
    {
        this.Title = title;
        this.Rating = rating;
        this.Price = price;
    }

    public override string ToString()
    {
        StringBuilder sb = new StringBuilder("Movie ");
        sb.Append("[Title=").Append(this.Title);
        sb.Append(", Rating=").Append(this.Rating);
        sb.Append(", Price=").Append(this.Price);
        sb.Append("]");

        return sb.ToString();
    }

}

只要我将<price>作为1.99,就可以完美运行。当我使用德语德语小数分隔符1,99时,它不再起作用了。

请咨询

3 个答案:

答案 0 :(得分:9)

如前所述,这并不是在XML中表示数值的有效方法。虽然这对字符串很好。你可以这样做:

[XmlIgnore]
public decimal Price {get;set;}

[XmlElement("price")]
public string PriceFormatted {
    get { return Price.ToString(...); }
    set { Price = decimal.Parse(value, ...); } 
}

其中“...”表示您选择的格式说明符和CultureInfo

答案 1 :(得分:4)

在XML-Schema规范中,double/decimal需要用.来表示,所以这种行为是设计的。

您可以使用字符串替换Price类型,然后使用具有适当RealpriceCultureInfo的Double.TryParse的非序列化属性NumberFormatInfo

[XmlRoot("movie")] 
public class Movie {     
      [XmlElement("price")]     
      public string Price { get; set; }  

      [XmlIgnore]
      public double RealPrice { 
         get { 
               double resultprice;
               if (!Double.TryParse(
                  Price, 
                  NumberStyles.Any, 
                  new CultureInfo("de-DE"),
                  resultprice)) throw new ArgumentException("price");
               // resultprice is now parsed, if not an exception is thrown
               return resultprice;
              } 
       }

答案 2 :(得分:1)

如前所述,XmlSerializer不适合您,因为它将使用W3C架构数据类型规范。

替代解决方案包括在反序列化之前使用XSLT文件转换输入XML,或者使用其他工具(如Linq到XML)。