问题描述
我在 xcode 9.3 和 xcode 10 beta 3 playground 中运行此代码
I am running this code in both xcode 9.3 and xcode 10 beta 3 playground
import Foundation
public protocol EnumCollection: Hashable {
static func cases() -> AnySequence<Self>
}
public extension EnumCollection {
public static func cases() -> AnySequence<Self> {
return AnySequence { () -> AnyIterator<Self> in
var raw = 0
return AnyIterator {
let current: Self = withUnsafePointer(to: &raw) { $0.withMemoryRebound(to: self, capacity: 1) { $0.pointee } }
guard current.hashValue == raw else {
return nil
}
raw += 1
return current
}
}
}
}
enum NumberEnum: EnumCollection{
case one, two, three, four
}
Array(NumberEnum.cases()).count
尽管两者都使用 swift 4.1,但它们给了我不同的结果
even though both are using swift 4.1 they are giving me different results for the
在 xcode 9.3数组大小为4
以及xcode 10 beta 3数组大小为0
我完全不明白.
推荐答案
这是一种获取所有枚举值序列的未公开方法,并且只是偶然地与早期的 Swift 版本一起工作.它依赖于枚举值的哈希值是连续整数,从零开始.
That is an undocumented way to get a sequence of all enumeration values,and worked only by chance with earlier Swift versions. It relies on thehash values of the enumeration values being consecutive integers,starting at zero.
这肯定不再适用于 Swift 4.2(即使运行在 Swift 4 兼容模式下)因为哈希值现在总是随机,参见 SE-0206 Hashable Enhancements:
That definitely does not work anymore with Swift 4.2 (even if runningin Swift 4 compatibility mode) because hash values are now alwaysrandomized, see SE-0206 Hashable Enhancements:
为了降低哈希值的可预测性,标准哈希函数默认使用每次执行的随机种子.
你可以用
print(NumberEnum.one.hashValue)
print(NumberEnum.two.hashValue)
不用 Xcode 10 打印 0
和 1
,但有些其他值也会随着每个程序的运行而变化.
which does not print 0
and 1
with Xcode 10, but someother values which also vary with each program run.
有关正确的 Swift 4.2/Xcode 10 解决方案,请参阅 如何枚举字符串类型的枚举?:
For a proper Swift 4.2/Xcode 10 solution, see How to enumerate an enum with String type?:
extension NumberEnum: CaseIterable { }
print(Array(NumberEnum.allCases).count) // 4
这篇关于Xcode 9 和 Xcode 10 给出不同的结果,即使使用相同的 swift 版本的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!