What's the deal with the following?
julia> @test 0.1 + 0.2 == 0.3 Test Failed Expression: 0.1 + 0.2 == 0.3 Evaluated: 0.30000000000000004 == 0.3 ERROR: There was an error during testing in record(::Base.Test.FallbackTestSet, ::Base.Test.Fail) at ./test.jl:397 in do_test(::Base.Test.Returned, ::Expr) at ./test.jl:281
The error is caused by the fact that none of
0.3 are represented in the computer as exactly those values —
3//10. Instead, they are approximated by values that are very close. But as seen in the test failure above, when adding two approximations together, the result can be a slightly worse approximation than is possible. There is much more to this subject that cannot be covered here.
But we aren't out of luck! To test that the combination of rounding to a floating point number and floating point arithmetic is approximately correct, even if not exact, we can use the
isapprox function (which corresponds to operator
≈). So we can rewrite our test as
julia> @test 0.1 + 0.2 ≈ 0.3 Test Passed Expression: 0.1 + 0.2 ≈ 0.3 Evaluated: 0.30000000000000004 isapprox 0.3
Of course, if our code was entirely wrong, the test will still catch that:
julia> @test 0.1 + 0.2 ≈ 0.4 Test Failed Expression: 0.1 + 0.2 ≈ 0.4 Evaluated: 0.30000000000000004 isapprox 0.4 ERROR: There was an error during testing in record(::Base.Test.FallbackTestSet, ::Base.Test.Fail) at ./test.jl:397 in do_test(::Base.Test.Returned, ::Expr) at ./test.jl:281
isapprox function uses heuristics based off the size of the numbers and the precision of the floating point type to determine the amount of error to be tolerated. It's not appropriate for all situations, but it works in most, and saves a lot of effort implementing one's own version of