当为具体类型实现时,我的二叉搜索树节点在游乐场中正常工作:
class Node {
var data: Int
var leftChild: Node?
var rightChild: Node?
init(data: Int){
self.data = data
}
}
let n = Node(data: 42) // {data 42 nil nil}
当我尝试将其设为通用时,Xcode崩溃并烧伤:
class GenericNode<T: Comparable> {
var data: T
var leftChild: GenericNode?
var rightChild: GenericNode?
init(data: T){
self.data = data
}
}
let g = GenericNode<Int>(data: 42)
当逐行输入时,Xcode会一直存在,直到我在init
中输入实际作业。我尝试指定<AnyObject: Comparable>
,但显然不允许向AnyObject
添加约束。如何在Swift中制作适当约束的通用容器?
答案 0 :(得分:1)
我认为这更可能是一个错误。如果您尝试在Swift
终端中执行此操作,则会抛出错误:
LVM ERROR:未实现的IRGen功能!非固定类布局
一种解决方法是让T
符合NSObject
。
由于NSObject
是一个协议,需要isEqual()
这样的方法,我认为这类似于Comparable
,的实现。 < / p>
所以,代码就像:
class GenericNode<T: NSObject> {
var data: T
var leftChild: GenericNode?
var rightChild: GenericNode?
init(data: T){
self.data = data
}
}
let g = GenericNode<NSNumber>(data: 42)
然后你可以像这样比较两个GenericNode
:
let f = GenericNode<NSNumber>(data: 53)
g.data.isGreaterThan(f.data) // is false in this case.
如果您只是尝试编写基本的BST内容,这应该足够好了。
答案 1 :(得分:1)
绝对是一些错误。此代码不会崩溃:
class GenericRootClass {
}
class GenericNode<T: GenericRootClass where T : Comparable> {
let data: T
var leftChild: GenericNode<T>?
var rightChild: GenericNode<T>?
init(data: T) {
self.data = data
}
}
但是只要我在类型约束中删除GenericRootClass或将其更改为Any或AnyObject,Xcode就会崩溃。
顺便说一句:你会在我的代码中注意到其他一些变化:
data
属性应该是不可变的。GenericNode<T>
,以便您可以实际与data
进行比较。 (编译器会指出那个,如果它可以存活足够长的时间。)像
这样简单class GenericRootClass<T> {
var data: T?
}
能够使Xcode 6 beta 2崩溃。看来普通类目前还没有工作。