Double.TryParse将0.1转换为1.0

时间:2013-09-30 11:46:52

标签: c# globalization cultureinfo tryparse

情况 - 我的网络应用程序中的线程文化已设置为“es”(西班牙语)

Thread.CurrentThread.CurrentUICulture = CultureInfo.CreateSpecificCulture("es");
Thread.CurrentThread.CurrentCulture = CultureInfo.CreateSpecificCulture("es");

字符串值为“0.1” 对于以下表达式,

var value = "0.1"
provider = CultureInfo.CreateSpecificCulture("en-US")
double.TryParse(value.ToString(), NumberStyles.Any, provider, out number)

数字返回1.0。这让我觉得它是从线程中挑选文化信息。不是我提供的那个。

以下单元测试通过(按预期)。

var numberInEnUS = "0.1";
var spanishCulture = CultureInfo.CreateSpecificCulture("es");
culture = new CultureInfo("en-US", false);
Thread.CurrentThread.CurrentCulture = spanishCulture;
Thread.CurrentThread.CurrentUICulture = spanishCulture;
double number;
double.TryParse(numberInEnUs, NumberStyles.Any, culture, out number);
Assert.AreEqual(0.1, number);

所以,问题是为什么double.TryParse在我的应用程序中失败?从理论上讲,西班牙语为0.1(西班牙语分隔符为小数点'。')。但是,数字1000.0不会转换为10000.因此,它似乎只失败了0.1 任何解释都非常感谢!

3 个答案:

答案 0 :(得分:1)

你说“0.1”是西班牙语中的数字。实际上不是,它是numberInEnglish或其他东西

var numberInSpanish = "0.1";//this is number in english culture

应该是

var numberInSpanish = "0,1";//<--Note 0,1
西班牙语的{p> NumberDecimalSeparator,。解析0,1你会得到预期的结果。

var numberInSpanish = "0,1";
var spanishCulture = CultureInfo.CreateSpecificCulture("es");
var culture = new CultureInfo("en-US", false);
Thread.CurrentThread.CurrentCulture = spanishCulture;
Thread.CurrentThread.CurrentUICulture = spanishCulture;
double number;
double.TryParse(numberInSpanish, NumberStyles.Any, spanishCulture, out number);

此处number被正确解析为“0.1”

答案 1 :(得分:0)

您的问题出在十进制和千位分隔符的混合中,即:

'' - “es”文化中的千位分隔符,解析时将被忽略(例如1.000,0 == 1000,0)

',' - “es”文化中的十进制分隔符,分隔整数和小数部分

您可以轻松说服自己:

  var spanishCulture = CultureInfo.CreateSpecificCulture("es");
  Char dS = spanishCulture.NumberFormat.NumberDecimalSeparator; // <- ','
  Char tS = spanishCulture.NumberFormat.NumberGroupSeparator;   // <- '.' 

因此,在您的情况下,字符串“0.1”将从'。'转换为1.0。如 在文化中成为一千个分隔符将被忽略。 你可以这样做:

  1. 使用不变文化而不是“es”one:

    double.TryParse(numberInNeutral,NumberStyles.Any,CultureInfo.InvariantCulture,out number);

  2. 或使用实际的西班牙语数字代表

    var numberInSpanish =“0,1”;

    double.TryParse(numberInSpanish,NumberStyles.Any,culture,out number);

答案 2 :(得分:0)

我终于能够找出问题所在。问题不在于TryParse()函数,而在于ToString()函数。

该值实际上是Double类型,而不是我上面提到的字符串。 (我的坏,我认为这不相关)。我实际上是在做一个值.ToString()。这是它使用线程文化并更改值的地方。 因此,如果值为0.1,则value.ToString()将其更改为“0,1”。它会根据Thread文化自动更改小数字符。然后,TryParse使用en-US文化并将“0,1”转换为1。

要修复它,请改用Convert.ToString并传入文化信息。

最后,这只是一个愚蠢的错误。

LessonLearnt - 在全球化应用程序中使用ToString()时要小心!