【问题标题】:XCTAssertEqual not working for double valuesXCTAssertEqual 不适用于双精度值
【发布时间】:2014-01-20 11:10:14
【问题描述】:

我正在为我正在编写的地图坐标函数编写一些单元测试。不幸的是,XCTest 发生了一些我无法确定的问题,导致我的测试失败:

NSString *testValue = @"121°31'40\"E";

double returnValue = coordinateStringToDecimal(testValue);
static double expectedValue = 121.5277777777778;
XCTAssertEqual(returnValue, expectedValue, @"Expected %f, got %f", expectedValue, returnValue);

我确实阅读了此similar question 以进行故障排除。但是,我能够验证数字和类型是否相同。这是检查每个值的类型的控制台输出:

(lldb) print @encode(__typeof__(returnValue))
(const char [2]) $5 = "d"
(lldb) print @encode(__typeof__(expectedValue))
(const char [2]) $6 = "d"

调试器中的变量视图显示它们是相同的:

有趣的是在 lldb 中比较它们的控制台输出:

(lldb) print (returnValue == expectedValue)
(bool) $7 = false

类型相同,实际数量相同。为什么我的断言会失败???

【问题讨论】:

    标签: objective-c unit-testing


    【解决方案1】:

    因为您处理的是浮点数,所以总会存在一定程度的不准确,即使在double 值之间也是如此。在这些情况下,您需要使用不同的断言:XCTAssertEqualWithAccuracy。来自文档:

    当 a1 在 + 或 - 精度范围内不等于 a2 时生成失败。此测试适用于浮点数和双精度数等标量,其中微小的差异可能会使这些项目不完全相等,但适用于所有标量。

    把你的断言改成这样:

    XCTAssertEqualWithAccuracy(returnValue, expectedValue, 0.000000001);
    

    或者在 Swift 4 中:

    XCTAssertEqual(returnValue, expectedValue, accuracy: 0.000000001, "expected better from you")
    

    在敏捷中:

    expect(expectedValue).to(beCloseTo(returnValue, within: 0.000000001))
    

    【讨论】:

    • 在 swift 3 中,添加了 accuracy 参数标签:XCTAssertEqualWithAccuracy(returnValue, expectedValue, accuracy: 0.000000001, "expected better from you");
    • 现在看起来像XCTAssertEqual 的重载允许accuracy 参数,就像XCTAssertEqualWithAccuracy 所做的那样。
    • 使用.ulpOfOne代替一些静态浮点值,相当于FLT/DBL_EPSILON
    【解决方案2】:

    在 Swift 4 中,从函数名称中删除了准确性 - 现在它是 XCTAssertEqual 的重载:

    XCTAssertEqual(returnValue, expectedValue, accuracy: 0.000000001, "expected better from you")
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2018-03-07
      • 2014-01-02
      • 1970-01-01
      • 2015-12-06
      • 2013-02-11
      • 2019-06-03
      相关资源
      最近更新 更多