Adding double values ​​is incompatible

I ran into the following problem while developing an engineering rule value mechanism using the eval (...) implementation.

Dim first As Double = 1.1 Dim second As Double = 2.2 Dim sum As Double = first + second If (sum = 3.3) Then Console.WriteLine("Matched") Else Console.WriteLine("Not Matched") End If 

'The above condition returns false, because the value of the sum is 3.3000000000000003 instead of 3.3

The 15th digit seems to be round. Someone can give a more detailed explanation for this pls.

Only the Math.Round (...) solution is available. OR is there something else I can try?

+4
source share
7 answers

You do not add decimal numbers - you add doubles.

Not all doubles can be accurately represented on the computer, therefore, an error. I suggest reading this article for the background (what every computer scientist should know about floating point arithmetic).

Use the decimal type instead; it does not suffer from these problems.

 Dim first As Decimal = 1.1 Dim second As Decimal = 2.2 Dim sum As Decimal= first + second If (sum = 3.3) Then Console.WriteLine("Matched") Else Console.WriteLine("Not Matched") End If 
+7
source

how a double number works on a PC. The best way to compare them is to use this design

 if (Math.Abs(second - first) <= 1E-9) Console.WriteLine("Matched") 

and if 1E-9 , you can use a different number that will represent a possible error in comparison.

+1
source

Comparison of equalities with floating point operations is always inaccurate due to the way the fractional values ​​are represented inside the machine. You must have some kind of epsilon value with which you are comparing. Here is an article that describes it in much more detail:

http://www.cygnus-software.com/papers/comparingfloats/Comparing%20floating%20point%20numbers.htm

Edit: Math.Round would not be an ideal choice due to the error generated with it for certain comparisons. You are better off defining an epsilon value that you can use to limit the number of errors when comparing (mainly determining the level of accuracy).

+1
source

A double uses floating point arithmetic, which is approximate but more efficient. If you need to compare with exact values, use the decimal data type instead.

+1
source

In C #, Java, Python, and many other languages, decimal numbers / floats are not perfect. Due to the way they are represented (using factors and exponents), they often have inaccuracies. See http://www.yoda.arachsys.com/csharp/decimal.html for details.

0
source

From the document: http://msdn.microsoft.com/en-us/library/system.double.aspx

Floating point values ​​and loss accuracy

Remember that a floating point number can only approximate a decimal number, and that the precision of a floating point number determines how exactly this number approaches a decimal number. By default, the Double Value contains 15 decimal digits of precision, although a maximum of 17 digits are stored internally. floating point precision has several consequences:

Two floating-point numbers appear equal to a specific precision; do not compare equal ones, because their smallest significant digits are different.

A mathematical or comparative operation that uses a floating point number may not give the same result if a decimal number is used, since a floating point number may not match exactly to approximate the decimal number.

The value cannot round if a floating point number. The value is considered rounded if the operation converts the original floating point number to another form, the reverse operation converts the converted form back to a floating point number, and the final floating point number is equal to the original floating point number. roundtrip may fail because one or the least significant digits are lost or changed in the conversion.

In addition, the result of arithmetic and assignment operations using Double values ​​may vary slightly by platform due to the loss of accuracy of the Double type. For example, the result of assigning a literal double value may differ in the 32-bit and 64-bit versions of the .NET Framework. The following example illustrates this difference when the literal value -4.42330604244772E-305 and a variable whose value is -4.42330604244772E-305 are assigned to a double variable. Note that the result of the Parse (String) method in this case does not suffer from a loss of precision.

0
source

This is a well known issue with floating point arithmetic. Look at binary coding for more information.

Use the decimal type if it suits your needs.

But in general, you should never compare floating point values ​​with constant floating point values ​​with an equal sign.

Otherwise, compare with the number of places you want to compare (for example, say that it is 4, then you would go (if total> 3.2999 and total <3.3001)

0
source

All Articles