如何在Dictionary <string,anyobject =“”> - Swift3中设置Array <object>

时间:2016-12-30 18:43:44

标签: swift3

我是新手。我正在尝试将数组添加到我的词典中的特定键。

我有以下代码:

var myArray : Array<Links> = []
var myDict : Dictionary<String, AnyObject> = [:]

myDict["links"] = myArray as AnyObject?  // I need help in this row, It does not work.

这是我在myDict中的Json结构,我正试图设置:

id : "blabla"
links: [
   0: {key1: "a", key2: "b", name: "c", link: "d"}
   1: {key1: "e", key2: "f", name: "j", link: "h"}
]

请考虑我已经完成所有其他工作了。我唯一的问题是如何在字典中添加我的数组,如上面代码中所述。

我的JSON结构:

enter image description here

我希望我能说清楚自己。 谢谢。

3 个答案:

答案 0 :(得分:2)

首先不要强制类型向上,除非编译器抱怨,否则不要注释类型。

其次,在Swift 3中,JSON字典是[String:Any]

此外,建议使用空集合对象的语法是

var myDict = Dictionary<String, Any>()

假设您的数组 - 实际上是字典 - 是

let myArray = [
    0: ["key1": "a", "key2": "b", "name": "c", "link": "d"],
    1: ["key1": "e", "key2": "f", "name": "j", "link": "h"]
]

只需指定它:

myDict["links"] = myArray

即使有结构

struct Link {
    var key1, key2, name, link : String
}

数组字典是

let linkDictionary = [
    0: Link(key1:"a", key2: "b", name: "c", link: "d"),
    1: Link(key1:"e", key2: "f", name: "g", link: "h")]

如果值类型为Any

,您可以指定它
myDict["links"] = linkDictionary

答案 1 :(得分:0)

假设,links实际上是一个数组,那将是:

var dictionary: [String: Any] = [
    "id": "blabla",
    "links": [
        ["key1": "a", "key2": "b", "name": "c", "link": "d"],
        ["key1": "e", "key2": "f", "name": "j", "link": "h"]
    ]
]

// retrieve links, or initialize it if not found

var links = dictionary["links"] as? [[String: String]] ?? [[String: String]]()

// add your new link to local dictionary

links.append(["key1": "k", "key2": "l", "name": "m", "link": "n"])

// update original structure

dictionary["links"] = links

就个人而言,当我看到像links这样的重复字典结构时,这会为这些对象的真实模型而尖叫。例如:

struct Foo {
    let id: String
    var links: [Link]?
}

struct Link {
    let key1: String
    let key2: String
    let name: String
    let link: String
}

var foo = Foo(id: "blabla", links: [
    Link(key1: "a", key2: "b", name: "c", link: "d"),
    Link(key1: "e", key2: "f", name: "j", link: "h") 
])

foo.links?.append(Link(key1: "k", key2: "l", name: "m", link: "n"))

现在,在后一个例子中,我假设links实际上是一个数组,而不是字典,但这并不是我的观点。我的关键观察是,如果使用适当的自定义类型而不仅仅是数组和字典,代码更具可读性和健壮性。

如果您需要向某些Web服务发送和接收这些模型对象,则可以将此模型对象映射到JSON和从JSON映射。但是请为您的实际模型使用自定义类型。

如果你想让上述类型很容易转换为JSON,你可以使用其中一个对象映射库,这样你就可以自己做一些事情,例如:

protocol Jsonable {
    var jsonObject: Any { get }
    init?(jsonObject: Any)
}

extension Foo: Jsonable {
    var jsonObject: Any {
        return [
            "id": id,
            "links": links?.map { $0.jsonObject } ?? [Any]()
        ]
    }

    init?(jsonObject: Any) {
        guard let dictionary = jsonObject as? [String: Any],
            let id = dictionary["id"] as? String else { return nil }

        var links: [Link]?
        if let linksDictionary = dictionary["links"] as? [Any] {
            links = linksDictionary.map { Link(jsonObject: $0)! }
        }

        self.init(id: id, links: links)
    }
}

extension Link: Jsonable {
    var jsonObject: Any { return [ "key1": key1, "key2": key2, "name": name, "link": link ] }

    init?(jsonObject: Any) {
        guard let dictionary = jsonObject as? [String: Any],
            let key1 = dictionary["key1"] as? String, 
            let key2 = dictionary["key2"] as? String, 
            let name = dictionary["name"] as? String, 
            let link = dictionary["link"] as? String else {
                return nil
        }
        self.init(key1: key1, key2: key2, name: name, link: link)
    }
}

然后你可以做类似的事情:

let object = try JSONSerialization.jsonObject(with: data)
var foo = Foo(jsonObject: object)!

或者:

foo.links?.append(Link(key1: "j", key2: "k", name: "l", link: "m"))

let data = try! JSONSerialization.data(withJSONObject: foo.jsonObject)

答案 2 :(得分:0)

这是解决方案:

   var arrLinks : Array<Dictionary<String, Any>> = []

   for link in myArray {                
       var dict : Dictionary<String, Any> = [:]

       dict["key1"] = link.name
       dict["key2"] = link.ghostBefore
       dict["key3"] = link.ghostAfter

       arrLinks.append(dict)               
    }

    myDict["links"] = arrLinks as AnyObject