Swift - 无法将BST节点转换为泛型

时间:2014-06-18 00:03:53

标签: generics swift

当为具体类型实现时,我的二叉搜索树节点在游乐场中正常工作:

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中制作适当约束的通用容器?

2 个答案:

答案 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就会崩溃。

顺便说一句:你会在我的代码中注意到其他一些变化:

  1. data属性应该是不可变的。
  2. 子节点的类型应为GenericNode<T>,以便您可以实际与data进行比较。 (编译器会指出那个,如果它可以存活足够长的时间。)
  3. 这样简单
    class GenericRootClass<T> {
        var data: T?
    }
    

    能够使Xcode 6 beta 2崩溃。看来普通类目前还没有工作。