Search code examples
c#stringdoublecalculatordata-conversion

Why does C# calculate double and decimal numbers wrongly?


I'm a beginner in C# and throughout my learning of the basics, I stumbled across a problem in which C# calculates two decimal/double numbers wrong. I'm doing a very basic calculator here. For example, if I want to add 2.1 and 3.1, the result will be 52, as if decimal points don't exist.

Console.Write("Enter a number: ");
double num1 = Convert.ToDouble(Console.ReadLine());

Console.Write("Enter Operator: ");
string op = Console.ReadLine();

Console.Write("Enter a second number: ");
double num2 = Convert.ToDouble(Console.ReadLine());


if (op == "+")
{
    Console.Write(num1 + num2);
}
else if (op == "-")
{
    Console.Write(num1 - num2);
}
else if (op == "/")
{
    Console.Write(num1 / num2);
}
else if (op == "*")
{
    Console.Write(num1 * num2);
}
else
{
    Console.Write("Invalid operator!");
}

Solution

  • Convert.ToDouble(String) parses the number in the current locale. So if your locale uses . for grouping digits and , as the radix point like the majority of Europe then 2.1 will be parsed as 21 and 2,1 means 2.1 in the English-speaking countries

    So one solution is to enter numbers in your locale: 2,1 and 3,1 instead

    Or you can also force Convert.ToDouble to use the specified locale by using the Convert.ToDouble(String, IFormatProvider) overload

    // Parse using the culture-independent format
    double num1 = Convert.ToDouble(Console.ReadLine(), CultureInfo.InvariantCulture);
    
    // Parse using German culture
    double num2 = Convert.ToDouble(Console.ReadLine(), new CultureInfo("de-DE"));
    
    // Parse using custom culture
    NumberFormatInfo provider = new NumberFormatInfo();
    provider.NumberDecimalSeparator = ",";
    provider.NumberGroupSeparator = ".";
    provider.NumberGroupSizes = new int[] { 3 };
    double num3 = Convert.ToDouble(Console.ReadLine(), provider);