簡體   English   中英

遍歷鍵以在Python中替換字符串

[英]Iterating Through Keys for String Replacement in Python

我正在嘗試通過pyMongo將YAML(JSON的各個行)插入到mongoDB中。 我的一些鍵包含句點,這會導致錯誤bson.errors.InvalidDocument: key 'job.no' must not contain '.' 根據這個SO答案 ,我將需要遍歷密鑰以替換句點,這很有意義。

我遇到的問題是我的數據混亂。 我的json包含嵌套的對象層,我不會事先知道包含句點的字符串是什么,或者它在哪里(哪個級別)。 這是我的數據的一小部分。

{"uuid":"94e31-02f59","project":{"name":"oasis","job.no":215493452,"subset":"beta"},"time":1412371841024}

我有一個遞歸地遍歷JSON的函數。 我嘗試了一些變體,但是它要么展平JSON(不再嵌套對象),要么僅返回第一個對象。 我想保持輸入的結構。

def keyCleaner(line):
    for k, v in line.iteritems():
        if isinstance(v, dict):
            keyCleaner(v)
        else:
            nK = k
            if "." in k:
                nK = k.replace(".", "_")
            return nK, v

當前返回的內容是:

(u'uuid', u'94e31-02f59')

我想要它返回的是:

{"uuid":"94e31-02f59","project":{"name":"oasis","job_no":215493452,"subset":"beta"},"time":1412371841024}

但是我不明白這是如何結合在一起的。 有人可以幫忙嗎?

那么這個遞歸解決方案呢? 請注意,由於標准Python的遞歸限制,深度嵌套的字典可能無法正常工作。

#!/usr/bin/env python

# parse initial string
import json

def keyCleaner(d):
    if type(d) is dict:
        for key, value in d.iteritems():
            d[key] = keyCleaner(value)
            if '.' in key:
                d[key.replace('.', '_')] = value
                del(d[key])
        return d
    if type(d) is list:
        return map(keyCleaner, d)
    if type(d) is tuple:
        return tuple(map(keyCleaner, d))
    return d

print keyCleaner(json.loads('{"uuid":"94e31-02f59","project":{"name":"oasis","job.no":215493452,"subset":"beta"},"time":1412371841024}'))

一個對我有用的麻煩的解決方案(但您需要跟蹤代碼中的修改)是簡單地包裝包含“。”的字典。 在python列表中並將列表存儲在mongo中,而不是存儲字典(這會引發錯誤)。

new_item_to_store = list(dict_to_store.items())

我在存儲域字典時遇到問題,即:

{"facebook.com": 2500,
"google.com" : 750,
"bing.com" : 200}

上面顯示了mongo store key 'job.no' must not contain '.'中的錯誤store key 'job.no' must not contain '.' ,但是效果很好:

[{"facebook.com": 2500,
"google.com" : 750,
"bing.com" : 200}]

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM