2

我有一个嵌套字典和一个包含路径片段的数组。我需要更新该位置的值。

我可能正在寻找递归函数而不是Dictionary类型的扩展等。

我无法递归地执行此操作,因为我制作了inout参数的副本。

var dict: [String: Any] = ["channel": ["item": ["title": 1111]]]
var pathFrag = ["channel", "item", "title"]
var val = 123

func addAt(pathFrag: inout [String], val: Int, data: inout [String: Any]) {
    if let first = pathFrag.first {
        if let item = data[first] {
            print(item)
            pathFrag.remove(at: 0)
            if !pathFrag.isEmpty {
                var d: [String: Any] = data[first] as! [String: Any]
                print("e: \(d)")
                return addAt(pathFrag: &pathFrag, string: string, data: &d)
            } else {
                data[first] = val
                print("else: \(data)")  // ["title": 123]
            }
        }
    }
}


addAt(pathFrag: &pathFrag, val: val, data: &dict)
print(dict)

如何更新 to 的title123

4

2 回答 2

2

这不是你问的,但这里的整个前提是 unSwifty。使用[String:Any]是一种难闻的气味。它看起来更像是 Objective-C。事实上,这整件事在 Objective-C 中是单行的:

NSMutableDictionary * d1 = [[NSMutableDictionary alloc] initWithDictionary: @{ @"title" : @1111 }];
NSMutableDictionary * d2 = [[NSMutableDictionary alloc] initWithDictionary: @{ @"item" : d1 }];
NSMutableDictionary * d3 = [[NSMutableDictionary alloc] initWithDictionary: @{ @"channel" : d2 }];

好吧,那只是为了准备数据。这是单线:

[d3 setValue:@123 forKeyPath:@"channel.item.title"];

但我会质疑整个嵌套字典的概念;在我看来,您在这里走错了路,您需要退后一步,重新考虑您的数据结构。

于 2019-03-16T17:00:31.463 回答
2

请注意,它var d: [String: Any] = data[first] as! [String: Any]会复制data[first]而不是引用它,例如&and inout。所以,当addAt(pathFrag: &pathFrag, string: string, data: &d)被调用时,只有d被改变。为了使这个改变反映在原来的data[first],你必须分配ddata[first]

做这个:

var dict: [String: Any] = ["channel": ["item": ["title": 1111]]]
var pathFrag = ["channel", "item", "title"]

func addAt(pathFrag: inout [String], data: inout [String: Any]) {
    if let first = pathFrag.first {
        if let item = data[first] {
            pathFrag.remove(at: 0)
            if !pathFrag.isEmpty {
                var d: [String: Any] = data[first] as! [String: Any]
                addAt(pathFrag: &pathFrag, data: &d)
                data[first] = d
            } else {
                data[first] = 123
            }
        }
    }
}


addAt(pathFrag: &pathFrag, data: &dict)
print(dict)
于 2019-03-16T15:53:08.433 回答