2017-02-28 57 views
0

我已经写了一个函数来获取excel列,并将它们放到字典中输出为json。当我写json输出时,键值看起来是随机排列的。有没有一种方法可以强制按照我添加的顺序输入关键值?如何避免字典项目订购密钥随机?

def excel_to_json(filename): 
    wb = xlrd.open_workbook(filename) 
    sh = wb.sheet_by_index(0) 

    # List to hold dictionaries 
    c_list = [] 

    # Iterate through each row in worksheet and fetch values into dict 
    for rownum in range(1, sh.nrows): 
     cars = OrderedDict() 
     row_values = sh.row_values(rownum) 
     cars['Name'] = row_values[0] 
     cars['Extensions'] = row_values[1] 
     cars['Patterns'] = row_values[2] 
     cars['RansomNoteFilenames'] = row_values[3] 
     cars['Comment'] = row_values[4] 
     cars['EncryptionAlgorithm'] = row_values[5] 
     cars['AlternateNames'] = row_values[6] 
     cars['Decryptor'] = row_values[7] 
     cars['AdditionalInfo1'] = row_values[8] 
     cars['AdditionalInfo2'] = row_values[9] 
     cars['Screenshots'] = row_values[10] 

     c_list.append(cars) 

    # Serialize the list of dicts to JSON 
    return formatJson(json.dumps(c_list)) 


def formatJson(input): 
    return json.dumps(json.loads(input), indent=4) 

一个例子JSON输出如下所示:如果处理

{ 
     "Name": "dummydata", 
     "Comment": "", 
     "AlternateNames": "", 
     "Screenshots": "dummydata", 
     "RansomNoteFilenames": "dummydata", 
     "Decryptor": "", 
     "Extensions": "dummydata", 
     "AdditionalInfo2": "", 
     "Patterns": "", 
     "EncryptionAlgorithm": "dummydata", 
     "AdditionalInfo1": "dummydata", 
    }, 

正如你可以看到这里的关键是在一个不同的顺序在for循环中excel_to_json()这使得JSON困难的可读性手动。

+1

您已经使用'OrderedDict'给出。你为什么再次转换成json? – AKS

+2

在你的formatJson函数中,你再次加载它(字典到字典),并导致问题 –

+0

ooops -deleting .... – knitti

回答

1

做这个

def formatJson(inp): 
    return json.dumps(inp, indent=4) 

,并调用它像

formatJson(c_list) 

你正在倾倒并重新装入一个额外的时间。

也略有改善你的代码

for rownum in range(1, sh.nrows): 
     cars = OrderedDict() 
     row_values = sh.row_values(rownum) 
     row_names = ['Name','Extensions','Patterns','Comment',....] 
     for i in range(len(row_values)): 
      cars[row_names[i]] = row_values[i] 

     c_list.append(cars) 
1

这取决于你实际使用的json串行是否荣誉的OrderedDict中的顺序。你可以尝试一个不同的(例如simplejson),看看它是否有效。它们都是API兼容的。

此外,大多数json.dumps实现有sort_keys参数,它将按字母顺序排序所有键。当您想要获得数据的稳定表示时,这非常有用,例如,差异等

p.s.

此外,如果您使用zip内建函数,则可以使您的代码更加简单。

columns = ['Name', 'Extension', 'Patterns'] 
row = ['Foo', 'Bar', 'Baz'] 
OrderedDict(zip(columns, row)) 

OrderedDict([('Name', 'Foo'), ('Extension', 'Bar'), ('Patterns', 'Baz')])