【问题标题】:XCT assert case of enumXCT 断言枚举的情况
【发布时间】:2021-07-20 08:34:28
【问题描述】:

我想断言一个值是否是一个特定的枚举大小写。
例如,如果我有以下枚举类和变量let value: MyEnum

enum MyEnum {
  case firstCase(value: Int)
  case secondCase
}

我想检查value 是否是firstCase 的实例。
本质上,我希望能够编写以下内容或类似内容:

let value: MyEnum = .firstCase(value: 3)
XCTAssertEnumCase(value, .firstCase)

我怎样才能做到这一点?我正在寻找一个已经存在的XCT 函数,或者寻找如何自己编写XCTAssertEnumCase 的说明。

【问题讨论】:

  • @Larme 断言大小写相等并不一定意味着断言相等。您经常希望您的Equatable 一致性也测试枚举案例的关联值的相等性,但是,同时,您可能需要仅测试您具有相同的枚举案例而不检查关联的测试价值。
  • 我是否正确理解您不想执行 XCTAssertEqual(value, .firstCase(value: 3)) 而是仅匹配 .firstCase?
  • @JoakimDanielson 是的,这是正确的。

标签: swift xctest


【解决方案1】:

您可以轻松地创建适用于特定 enums 的函数,但是,创建适用于任何枚举的通用断言函数将很难实现,因为没有协议/类型约束可以代表任何 @987654322 @。您可以将RawRepresentable 用于具有原始值的枚举,但这不会涵盖所有enums,例如您的问题中的那个。

这是您特定枚举的函数。

func XCTAssertEnumCase(_ testValue: MyEnum, _ expectedValue: MyEnum) -> Bool {
    switch (testValue, expectedValue) {
    case (.firstCase, .firstCase):
        return true
    case (.secondCase, .secondCase):
        return true
    default:
        return false
    }
}

或者,您可以使您的枚举符合您的测试目标中的Equatable(如果它尚未符合您的实际生产目标),并且只检查您的Equatable 一致性中的大小写相等性,但是您将不会无法轻松测试“完全相等”(包括相关值)。此外,该解决方案将要求您为正在测试的所有协议手动实现Equatable 一致性。

如果没有实际提供关联值,则无法实例化具有关联值的枚举案例。所以XCTAssertEnumCase(value, .firstCase)无法实现。

你可以做XCTAssertEnumCase(testValue, .firstCase(value: 3313),你可以将任何Int传递给firstCase的关联值,只要testValue也是firstCase,函数将返回true,不管关联值。

或者,您可以创建单独的函数来断言枚举的每个案例。

extension MyEnum {
    func assertFirstCase() -> Bool {
        switch self {
        case .firstCase:
            return true
        default:
            return false
        }
    }

    func assertSecondCase() -> Bool {
        switch self {
        case .secondCase:
            return true
        default:
            return false
        }
    }
}

然后像这样使用它:

let value: MyEnum = .firstCase(value: 3)
value.assertFirstCase() // returns true
value.assertSecondCase() // returns false

【讨论】:

  • 也许我理解错了,但是您对XCTAssertEnumCase 的实现不允许我这样调用它,对吧? XCTAssertEnumCase(value, .firstCase)。我会收到一个错误提示 Member 'firstCase' expects argument of type 'Int'?我正在明确地寻找一种方法,而无需为 expectedValue 提供参数。
  • @nhaarman 没有办法做到这一点。如果不提供关联值,则无法实例化具有关联值的枚举案例。但是,您可以传入任何默认值,并且该函数将在大小写相等检查期间将其丢弃。我知道这不能 100% 满足您的需求,但不幸的是,您正在寻找的东西在 Swift 中根本不可能。
  • 真可惜。特别是因为可以写if case .firstCase = value,但无法将其提取为通用函数。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2019-06-03
  • 2020-03-30
  • 1970-01-01
  • 2021-10-25
  • 2019-02-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多