无法投射类型' Swift.UInt64' (0x10dddde88)到' Swift.AnyObject' (0x12129d018)

时间:2016-12-15 06:35:52

标签: ios swift swift2

在Swift 2.3中,我必须使用UInt64AnyObject投射到as!。但它是Swift 3中的as。一旦我在Swift 2.3中使用它,它就会崩溃,并发出以下消息。

  

无法转换类型' Swift.UInt64' (0x10dddde88)到' Swift.AnyObject' (0x12129d018)。

请帮帮我。谢谢!

2 个答案:

答案 0 :(得分:1)

Swift 3与Swift 2.3的不同之处在于铸造。例如,如果您在Xcode 8游乐场中运行以下内容(使用最新的Swift工具链,在我的情况下使用Xcode 8.2):

import Foundation
import Swift

struct Foo
{
    init()
    {

    }
}

NSStringFromClass(type(of: Foo() as AnyObject))

您会看到,NSStringFromClass(type(of: Foo() as AnyObject))会在右侧的检查栏中注册为"_SwiftValue"

这是因为Swift 3允许您使用内部AnyObject类将任何构造包装为_SwiftValue,然后可以将其解包到您的其他部分中。代码。

Swift 2.3 没有此功能。那是你犯错的地方。

但你可以做的是将UInt64投射到NSNumber。如果我没记错的话,这适用于Swift 2.3和3.0。我意识到您可能正在处理泛型类型,并且在编译期间您可能不知道您正在处理的类型是UInt64还是其他类型;但这种方法无论如何都应该有效您也可以使用as?运算符来处理转换错误和异常。

答案 1 :(得分:0)

在Swift 2中,只有IntUInt可以转换为AnyObject(隐式或显式)。

当您明确地将IntUInt转换为AnyObject时,您使用as投射,而不是as!

//Swift 2.3
let ui: UInt = 1234
let uiObj = ui as AnyObject

let i: Int = 5678
let iObj = i as AnyObject

实际上,它们会自动转换为NSNumber

//Swift 2.3
print(uiObj.dynamicType) //->__NSCFNumber (__NSCFNumber is one of the concrete subclasses of NSNumber)
print(iObj.dynamicType)  //->__NSCFNumber

在Swift 3中,删除了一些隐式转换,但是从3.0.1开始,所有整数类型都可以通过显式转换转换为NSNumber

//Swift 3.0.2
let ui64: UInt64 = 12345678
let ui64Obj = ui64 as AnyObject

let i8: Int8 = 123
let i8Obj = i8 as AnyObject

let ui: UInt = 1234
let uiObj = ui as AnyObject

let i: Int = 5678
let iObj = i as AnyObject

print(type(of: ui64Obj)) //->_SwiftTypePreservingNSNumber (_SwiftTypePreservingNSNumber is another subclass of NSNumber)
print(type(of: i8Obj))   //->_SwiftTypePreservingNSNumber
print(type(of: uiObj))   //->_SwiftTypePreservingNSNumber
print(type(of: iObj))    //->_SwiftTypePreservingNSNumber

因此,如果你想在Swift 3中使用Swift 3中的uint64Value as AnyObject得到几乎相同的结果,则需要明确构造NSNumber

//Swift 2.3
let ui64: UInt64 = 12345678
let ui64Obj = NSNumber(unsignedLongLong: ui64)
print(ui64Obj.dynamicType)  //->__NSCFNumber

uint64Value as AnyObject替换为NSNumber(unsignedLongLong: uint64Value)

(事实上,_SwiftTypePreservingNSNumber__NSCFNumber并不完全相同,但这可能不是您的问题。)

顺便说一句,当我在Xcode 8.2中将Legacy Swift标志设置为YES时,它会显示警告:

  

Swift 2.3已弃用,将在以后的版本中删除   Xcode中。现在迁移到Swift 3。

Apple非常鼓励我们立即转向Swift 3.

您最好赶快将代码迁移到Swift 3。