Swift and Codable:可编码树结构,其值终止于遵守自定义协议

时间:2019-04-15 15:03:07

标签: json swift parsing codable

我正在尝试使树数据结构服从可编码协议。树终止于遵循协议“ Terminal”的“ some object”。终端扩展了可编码。

树的每个节点都是一对。它有一个键和一个值。该值可以是对,也可以是终端。

主要有两个问题:

1) 我希望这种结构编码为JSON,例如

class Pair: Codable {
   var key: String?
   var value: Codable?
}

let outputSimple = Pair(key: "a test key", value: "a test value")
// encodes to
// {"a test key": "a test value"}
// whereas currently encodes to
// {}

let outputComplex = Pair(key: "a parent", value: Pair(key: "another pair", value: "a test value"))
// encodes to
// {"a parent": {"another pair", "a test value"}}

编辑:第2部分可能会稍微混淆该问题。为了澄清上述问题,如果我有

class Pair: Codable {
   var key: String
   var value: String
}
let p = Pair(key:"foo", value: "bar")

如何获取输出{“ foo”:“ bar”}而不是{key:foo,value:bar}的信息?我尝试过

    override func encode(to encoder: Encoder) throws {
        var container = encoder.unkeyedContainer()
        container.encode(contentsOf: [key: value])
    }

但出现错误“实例方法'encode(contentsOf :)'要求'((键:_,值:_)')符合'可编码'''

2)我正在尝试以下操作,但似乎没有用。我得到“对不符合协议“可解码””

protocol TreeNode: Codable {} 
struct Pair: TreeNode {
   var key: String?
   var value: TreeNode?
}

extension String: TreeNode {}

我可以通过使TreeNode成为Pair的子类来解决这个问题。这很可能是正确的Swift行为。但是,我想知道是否有更多的眼睛可以解释这个问题。我假设只要确保所有值都是对类型,或者是其他遵循Codable的值,那么它将起作用。

1 个答案:

答案 0 :(得分:3)

这不起作用。

value必须是符合Codable的具体类型,而不是协议本身或符合Codable的第二协议

您可以做的是将value声明为通用

class Pair<T: Codable>: Codable {
    var key: String?
    var value: T?

    init(key: String?, value: T?) {
        self.key = key
        self.value = value
    }
}

它可以对outputSimpleoutputComplex进行编码