swift - 你能在 swift 中强制执行类型别名吗

标签 swift types

我试图强制由 Int 支持的简单类型不会与其他 Int 混合。

假设您有以下类型别名:

typealias EnemyId = Int
typealias WeaponId = Int

我希望以下内容出现编译器错误:

var enemy: EnemyId = EnemyId("1")
enemy = WeaponId("1") // this should fail

我想要失败的行应该失败,因为两种类型(EnemyId 和 WeaponId)是不同的类型。

实现这一目标的最好、最干净的方法是什么?

更新

查看答案和评论后,我想添加我使用枚举想到的内容:

enum Enemy {
    case id(Int)
    var id: Int {
        switch self {
        case .id(let i):
            return i
        }
    }
}
let enemy = Enemy.id(1)
print("enemy: \(enemy.id)")

目前,Mattt 的答案要短得多,也更符合您对 Swift 的期望。

更新#2

我还无法访问 swift 4.1,因此我必须执行以下操作:

  struct EnemyId : Hashable {
    private let value: Int

    init(_ value: Int) {
      self.value = value
    }

    init?(_ string:String) {
      guard let value = Int(string) else { return nil }
      self.init(value)
    }

    static func ==(_ lhs: EnemyId, _ rhs: EnemyId) -> Bool {
      return lhs.value == rhs.value
    }

    var hashValue: Int {
      return value.hashValue
    }
  }

然而,它给我的解析增加了几百毫秒,因此我不得不恢复到类型别名,但这非常接近我想要的。

最佳答案

请注意,在 Swift 4.1 中,像 Rob 和 Cristik 这样的包装结构建议编写起来变得微不足道,因为当您声明采用 Hashable 时,您将获得 hashValue自动合成实现==在幕后。

因此,为了您的目的,编写以下内容可能就足够了:

struct EnemyId: Hashable {
    let value: Int
}
struct WeaponId: Hashable {
    let value: Int
}

在这两种情况下,您都可以“免费”获得成员初始化器 init(value:) 加上 == 加上 hashValue

关于swift - 你能在 swift 中强制执行类型别名吗,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48813776/

相关文章:

ios - 重新加载数据时刷新 tableView 闪烁

swift - 拖动手势时将矩形限制到屏幕边缘

ios - 导航栏标题不粗体

ios - 如何解决webView及其子view的Gesture冲突?

c - 如何将字符串拆分为不同的类型(int 表示数值,char 表示字母)?

ios - 不尊重 UIButton 的 backgroundImage 的内容模式

c - 有符号整数的平台独立存储

java - Wild FJ 论文中类型变量和类型参数的区别?

python - pydantic:对具有别名的字段使用 property.getter 装饰器

types - 为什么编译器需要特征的实现才能调用默认的自由函数?