gpt4 book ai didi

ios - fatal error : could not demangle keypath type

转载 作者:行者123 更新时间:2023-12-01 15:26:35 28 4
gpt4 key购买 nike

我有一个简单的类,我想在 init 中使用 keypath ,像这样:

class V: UIView {
convenience init() {
self.init(frame: .zero)
self[keyPath: \.alpha] = 0.5
}
}

let v = View()
当我运行此代码时,出现运行时错误:

Fatal error: could not demangle keypath type from ' ����XD':


但是,如果我在 keyPath 中指定类型它工作正常:
class V: UIView {
convenience init() {
self.init(frame: .zero)
self[keyPath: \UIView.alpha] = 0.5
}
}

let v = View()
print(v.alpha) \\ prints 0.5
但是,更奇怪的是这段代码有效:
class V: UIView {
convenience init() {
self.init(frame: .zero)
foo()
}

func foo() {
self[keyPath: \.alpha] = 0.5
}
}

let v = View()
print(v.alpha) \\ prints 0.5
此错误的实际原因是什么?

最佳答案

不出所料,这是一个编译器错误。事实上,it was reported仅在您发布问题前几周。错误报告包含一个稍微简单的例子,它触发了同样的崩溃:

class Foo: NSObject {
@objc let value: String = "test"

func test() {
let k1 = \Foo.value // Ok
let k2 = \Self.value // Fatal error: could not demangle keypath type from '�: file /AppleInternal/BuildRoot/Library/Caches/com.apple.xbs/Sources/swiftlang/swiftlang-1103.8.25.8/swift/stdlib/public/core/KeyPath.swift, line 2623
}
}

Foo().test()
事实证明,Swift 编译器没有正确处理包含协变 Self 的关键路径。类型。如果您需要复习, covariant Self type or dynamic Self type允许您指定方法或属性始终返回 self 的类型即使该类是子类。例如:
class Foo {
var invariant: Foo { return self }
var covariant: Self { return self }
}
class Bar: Foo {}

let a = Bar().invariant // a has compile-time type Foo
let b = Bar().covariant // b has compile-time type Bar

func walkInto(bar: Bar) {}
walkInto(bar: a) // error: cannot convert value of type 'Foo' to expected argument type 'Bar'
walkInto(bar: b) // works
但是您的示例不使用动态 Self !实际上确实如此:在便利初始化程序的上下文中, self 的类型实际上是动态 Self类型,因为也可以调用便利初始化程序来初始化您的类的子类 V .
那么究竟出了什么问题呢?好吧,Swift 编译器没有包含任何处理动态的逻辑 Self创建 key 路径时。在幕后,它本质上试图发出类型为 ReferenceWritableKeyPath<Self, CGFloat> 的关键路径对象。 .类型系统不允许您使用动态 Self在这种情况下,运行时并没有预料到它。您收到的奇怪错误消息是尝试解码此意外对象类型的结果,该类型被编码为指向 V 元数据的 4 字节相对指针。类,后跟 XD indicating a dynamic Self type (因此错误消息包含 4 个 后跟 XD )。通过玩弄 different ways to create key paths involving dynamic Self ,我在编译时和运行时都遇到了许多不同的崩溃。
我已提交 a fix对于这个错误。结果很简单:基本上,我们到处都能找到动态 Self创建关键路径时,我们只需将其替换为静态 self 并在必要时添加向下转换。动态 Self仅在编译时强制执行程序正确性;它可以而且应该在运行前从程序中剥离出来。

关于ios - fatal error : could not demangle keypath type,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/61137449/

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