Некорректно преобразуется строка в число с плавающей точкой в C#

string str4 = Console.ReadLine();
double number4 = double.Parse(str4, CultureInfo.InvariantCulture)
Console.WriteLine(number4);

При введении строки с консоли через точку и последующей конвертации в число всё работает правильно. Но если вводить через запятую, то при конвертации эта запятая как будто исчезает (т.е. ввёл строку 5,6 - получил конечное число 56). Что не так?


Ответы (1 шт):

Автор решения: VladD

Вы парсите вашу строку в InvariantCulture. В этой культуре символ точки является десятичным разделителем, а символ запятой — разделителем тысяч, поэтому запятая просто игнорируется.

Если вы хотите, чтобы запятая, а не точка, была десятичным разделителем, используйте язык, в котором она такой и является, например, русский:

CultureInfo ru = CultureInfo.GetCultureInfo("ru-RU");
double v = double.Parse("5,6", ru); // 5.6

Если вы хотите, чтобы точка была десятичным разделителем, а запятая не игнорировалась, вам нужно подправить NumberStyles:

double.Parse(
   "5,6",
   NumberStyles.Number & ~NumberStyles.AllowThousands,
   CultureInfo.InvariantCulture);

производит

System.FormatException: 'Input string was not in a correct format.'


Если очень хочется, чтобы числа вводились по правилам и русского, и английского языков, используйте TryParse:

string s = "5,6";
CultureInfo en = CultureInfo.GetCultureInfo("en-US");
CultureInfo ru = CultureInfo.GetCultureInfo("ru-RU");
NumberStyles noThousands = NumberStyles.Number & ~NumberStyles.AllowThousands;

double v;
if (double.TryParse(s, noThousands, en, out v))
    Console.WriteLine($"Parsed as English: {v}");
else if (double.TryParse(s, noThousands, ru, out v))
    Console.WriteLine($"Parsed as Russian: {v}");
else
    Console.WriteLine("Cannot parse");

При этом у вас потеряется возможность вводить разделители тысяч (которые у нас практически никто не использует, а как в других странах — depends).

→ Ссылка