gpt4 book ai didi

swift - Swift 中的 'non-nominal type' 是什么?

转载 作者:IT王子 更新时间:2023-10-29 05:06:03 27 4
gpt4 key购买 nike

我在尝试扩展诸如 (Int, Int)Any 之类的非正统“类型”时看到此错误:

Non-nominal type 'Any' cannot be extended

那么什么使类型成为非标称类型呢?像 Any(Int) 这样的非标称类型和像 Int 这样的常规标称类型有什么区别?

最佳答案

currently accepted answer 不正确;实际答案来自 Swift 类型系统的一个深奥的部分。

Swift 中的大多数类型都是标称类型——它们是作为用户代码的一部分在特定模块中声明的“命名”类型。 IntArray 等看似原始的类型实际上是 Swift 模块中定义的结构,它会自动导入到每个 Swift 源文件中。甚至 Optional 本身也是 Swift 模块中的枚举,尽管编译器添加了一些魔法,例如可选链接和强制展开。

少数异常(exception)被称为“非标称类型”。可能还有其他的,但主要的是:

  • 函数类型,例如 (Int) -> String
  • 元组类型,例如 (Int, String)
  • 元类型,例如 String.Type(表达式 String.self 的类型)
  • 存在性,例如 CustomStringConvertible & Error

存在主义值得更多解释。存在性包含一个值,其确切类型已被抽象掉,但已知它符合一组特定的协议(protocol)。例如:

// You can put anything that conforms to `CustomStringConvertible` in `x`
let x: CustomStringConvertible

// You can put anything that conforms to both `CustomStringConvertible`
// and `Error` in `y`
let y: CustomStringConvertible & Error

// You can put anything in `z`; `Any` is an existential that doesn't
// require you to conform to any particular protocols
let z: Any

非标称类型都是以某种特别的方式简单地将其他类型组合在一起。 (它们有时被称为“结构类型”,因为它们为其他类型定义了某种通用结构。)它们不需要明确定义,它们不属于任何特定模块——FooKit 的 (Int, String) 是与 BarKit 的 (Int, String) 相同。但是它们的所有行为都是由语言定义的——非标称类型不能有自己的方法或属性,不能符合协议(protocol),因此不能扩展。

所以你不能扩展 Any,因为 Any 是一种内置于语言中的特殊事物,就像函数类型或元组类型一样。它恰好有一个用字母而不是标点符号写的名字。

(那么为什么可以扩展 CustomStringConvertible?因为,根据上下文,CustomStringConvertible 可能意味着协议(protocol),或者它可能意味着包含符合协议(protocol)的值的存在。当你写 extension CustomStringConvertible 时,你在扩展协议(protocol),但是当你写 let x: CustomStringConvertible 时,你声明了一个变量,其类型是“包含符合协议(protocol)的值的存在”。这有点令人困惑,Swift 的一些维护者会实际上喜欢要求将 existential 写为 Any<CustomStringConvertible> 以使其更清楚。不过,现在不太可能发生,因为他们正试图保持源稳定性。)

关于swift - Swift 中的 'non-nominal type' 是什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24131466/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com