I got multiple dictionaries in json format 'some.json' looking like these
{
"my_dict" : {
'key1': 'value1',
'key2': 'value2',
'key3': 'value3'
},
"my_dict2" : {
'key8': 'value8',
'key9': 'value9',
'key10': 'value10'
}
}
Both key and value are strings. I would like to export it to csv
format vertically then read it back to json
file. For example, when I add an item to my_dict on csv
format then it would also be added on the json
file.
Required output
my_dict
key1,value1
key2,value2
key3,value3
my_dict2
key8,value8
key9,value9
key10,value10
I got so far a solution, but the problem is, the name of the dictionaries are not written on the csv file so can't be read back to json file
import pandas as pd
with open('some.json') as f_input:
df = pd.read_json(f_input)
df = df.bfill(axis='columns')
df.iloc[:, 0].to_csv('some.csv', encoding='utf-8', header=False)
CodePudding user response:
I fixed your some.json
file:
{
"my_dict": {
"key1": "value1",
"key2": "value2",
"key3": "value3"
},
"my_dict2": {
"key8": "value8",
"key9": "value9",
"key10": "value10"
}
}
Now you can convert your json file into a csv file:
pd.read_json('some.json', orient='index').stack().to_csv('some.csv', header=False)
Your some.csv
file looks like:
my_dict,key1,value1
my_dict,key2,value2
my_dict,key3,value3
my_dict2,key8,value8
my_dict2,key9,value9
my_dict2,key10,value10
Note: with the above format, you can easily use your csv file in Excel if you need it.
The rollback operation:
d = pd.read_csv('some.csv', header=None, index_col=0).groupby(0, sort=False) \
.apply(lambda x: {k: v for k, v in zip(x[1], x[2])}).to_dict()
print(d)
# Output:
{'my_dict': {'key1': 'value1', 'key2': 'value2', 'key3': 'value3'},
'my_dict2': {'key8': 'value8', 'key9': 'value9', 'key10': 'value10'}}
CodePudding user response:
Create new file with file.write
for names of dict:
import json
with open('some.json') as f:
d = json.load(f)
#sample
d = { "my_dict" : { 'key1': 'value1', 'key2': 'value2', 'key3': 'value3'},
"my_dict2" : { 'key8': 'value8', 'key9': 'value9', 'key10': 'value10'}}
with open("some1.csv", 'w') as f:
for k, v in d.items():
f.write(k '\n')
for k1, v1 in v.items():
f.write(f"{k1},{v1}\n")
my_dict
key1,value1
key2,value2
key3,value3
my_dict2
key8,value8
key9,value9
key10,value10
And for read back:
df = pd.read_csv("some1.csv", names=['a','b'])
m = df['b'].isna()
df['new'] = df['a'].where(m).ffill()
s = df[~m].set_index(['new','a'])['b']
d = {level: s.xs(level).to_dict() for level in s.index.levels[0]}
print (d)
{'my_dict': {'key1': 'value1', 'key2': 'value2', 'key3': 'value3'},
'my_dict2': {'key8': 'value8', 'key9': 'value9', 'key10': 'value10'}}
EDIT:
If format should be changed:
d = { "my_dict" : { 'key1': 'value1', 'key2': 'value2', 'key3': 'value3'},
"my_dict2" : { 'key8': 'value8', 'key9': 'value9', 'key10': 'value10'}}
with open("some1.csv", 'w') as f:
for k, v in d.items():
for k1, v1 in v.items():
f.write(f"{k},{k1},{v1}\n")
my_dict,key1,value1
my_dict,key2,value2
my_dict,key3,value3
my_dict2,key8,value8
my_dict2,key9,value9
my_dict2,key10,value10
s = pd.read_csv("some1.csv", names=['b'], squeeze=True)
print (s)
my_dict key1 value1
key2 value2
key3 value3
my_dict2 key8 value8
key9 value9
key10 value10
Name: b, dtype: object
d = {level: s.xs(level).to_dict() for level in s.index.levels[0]}
print (d)
{'my_dict': {'key1': 'value1', 'key2': 'value2', 'key3': 'value3'},
'my_dict2': {'key8': 'value8', 'key9': 'value9', 'key10': 'value10'}}
CodePudding user response:
A little hacky but produces exactly the input you are after:
[f'{col}\n{df[col].dropna().to_csv(header=False)}' for col in df.columns)]
You can either ''.join(...)
and then write in a single go or add mode='a',
to to_csv
so that the output is appended directly to some file.