DataSet.GetXml()数值精度问题的解决办法及微软bug反馈渠道咨询
.NET Core 6.0 DataSet.GetXml() 数值精度异常问题解决及反馈渠道
在使用.NET Core 6.0时,调用DataSet.GetXml()将数据集转换为XML字符串时,部分double类型数值出现精度异常,例如输入56.45533,转换后变为56.455329999999996。调试时可见生成的XML中,多个double数值存在类似的精度偏差。
问题复现代码
DataSet ds = new DataSet(); DataTable dt = new DataTable("Forecast"); dt.Columns.Add(new DataColumn("lat", typeof(double))); DataRow dr1 = dt.NewRow(); DataRow dr2 = dt.NewRow(); DataRow dr3 = dt.NewRow(); DataRow dr4 = dt.NewRow(); DataRow dr5 = dt.NewRow(); dr1["lat"] = 56.45533; dt.Rows.Add(dr1); dr2["lat"] = 59.67768; dt.Rows.Add(dr2); dr3["lat"] = 534.64568; dt.Rows.Add(dr3); dr4["lat"] = 56.45533; dt.Rows.Add(dr4); dr5["lat"] = 534.47755; dt.Rows.Add(dr5); ds.Tables.Add(dt); var temp = ds.GetXml();
解决办法
- 改用decimal类型存储数值:decimal是精确小数类型,不会出现二进制浮点数的精度丢失问题。修改列类型为
typeof(decimal),赋值时使用decimal字面量(加m后缀):dt.Columns.Add(new DataColumn("lat", typeof(decimal))); dr1["lat"] = 56.45533m; - 自定义XML序列化逻辑:如果必须使用double类型,可以通过
XmlWriter手动序列化数据,对数值进行格式化,保留指定小数位数:using (var sw = new StringWriter()) using (var writer = XmlWriter.Create(sw, new XmlWriterSettings { Indent = true })) { writer.WriteStartDocument(); writer.WriteStartElement("DataSet"); writer.WriteStartElement("Forecast"); foreach (DataRow row in dt.Rows) { writer.WriteStartElement("Forecast"); writer.WriteElementString("lat", ((double)row["lat"]).ToString("F5")); // 保留5位小数,可按需调整 writer.WriteEndElement(); } writer.WriteEndElement(); writer.WriteEndElement(); writer.WriteEndDocument(); var temp = sw.ToString(); }
向微软反馈问题的渠道
前往GitHub的dotnet/runtime仓库提交Issue,提交时需提供以下信息:
- .NET版本(明确为6.0)
- 完整的复现代码
- 问题现象描述及相关截图
- 预期输出与实际输出的对比
内容的提问来源于stack exchange,提问作者Rushikesh Sane
相关产品推荐
相关产品推荐

