How to not quote empty values with csv.QUOTE_NONNUMERIC? - python-3.x

I'm using a dictwriter as follows:
csv.DictWriter(output_file, keys, delimiter=';', quotechar='"', quoting=csv.QUOTE_NONNUMERIC)
which gives me the desired output when all keys have non-numeric values:
key1;key2;key3
"value1";"value2";"value3"
now i have keys without values and the dictwriter quotes the empty strings as well:
dic.update(key2=None)
{'key1':'value1', 'key2': None, 'key3':'value3'}
key1;key2;key3
"value1";"";"value3"
what i would like to have is:
key1;key2;key3
"value1";;"value3"
how's that possible? any idea?

i wasn't able to find a trivial solution, so i decided to open the existing file and to replace those "" values:
text = open(filename, 'r')
text = ''.join([i for i in text]) \
.replace('""', '')
x = open(filename,'w')
x.writelines(text)
x.close()
that gave me the desired output
from:
key1;key2;key3
"value1";"";"value3"
to:
key1;key2;key3
"value1";;"value3"
all good.. but.. is there a neater way of doing this?

Use csv.QUOTE_MINIMAL where you have None type in dictionary and use csv.QUOTE_NONNUMERIC elsewhere:
>>> d = {'key1': 'value1', 'key2': None, 'key3': 'value3'}
>>> for k,v in d.items():
if d[k] is None:
with open('test.csv', 'w') as f:
w = csv.DictWriter(f, d.keys(), csv.QUOTE_MINIMAL)
w.writeheader()
w.writerow(d)
else:
with open('test.csv', 'w') as f:
w = csv.DictWriter(f, d.keys(), csv.QUOTE_NONNUMERIC)
w.writeheader()
w.writerow(d)
Output:
key1,key2,key3
value1,,value3

Related

yaml dump a python dictionary without quotes

when I try to dump a python dictionary to yaml file, I get results with quotes both keys and values.
For example I create a python dictonary:
d = { 'a': '1', 'b': '2' }
with open(attributes_file, "w") as fw:
yaml.dump(dict_attributes, fw)
I get this output:
'a': '1'
'b': '2'
How to remove quotes?
You must convert values to int like this
d2 = {k: int(v) for k,v in d.items()}
and save d2 dict.

Pandas print unique values as string

I've got a list of unique value from selected column in pandas dataframe. What I want to achieve is to print the result as string.
import pandas as pd
df = pd.DataFrame({'A':['A','C','C','B','A','C','B']})
a = df['A'].unique()
print(a)
Output: ['A' 'C' 'B']
Desired output: A, C, B
So far I've tried below,
print(a.to_string())
Got this error: AttributeError: 'numpy.ndarray' object has no attribute 'to_string'
print(a.tostring())
Got this: b'\xf0\x04\xa6P\x9e\x01\x00\x000\xaf\x92P\x9e\x01\x00\x00\xb0\xaf\x92P\x9e\x01\x00\x00'
Can anyone give a hint.
import pandas as pd
df = pd.DataFrame({'A':['A','C','C','B','A','C','B']})
a = df['A'].unique()
print(', '.join(a)) # or print(*a, sep=', ')
Prints:
A, C, B
EDIT: To store as variable:
text = ', '.join(a)
print(text)
This should work:
print(', '.join(a))
py3 solution
df = pd.DataFrame({'A':['A','C','C','B','A','C','B']})
a = df['A'].unique()
print(*a, sep=", ")

Adding keys and value pair to a dictionary within a dictionary with duplicate keys

results is a list within a list with the data as shown in the results section. I am hoping to achieve a dictionary within a dictionary as shown in the results portion.
input:
results = [['abc','12'3,'1123','qwe', 'asd'],['abc','123,'1123','qwe', '123'],['abc','123','1123','ewq','zxc'], ['bcd','123','1123','ewq','zxc'], ['bcd','123','1123','ewq','zxc]]
Code:
report_dict = dict()
axis_list = []
results = self.report_data(conn)
for row in results:
try:
report_dict[row[0]] = {}
report_dict[row[0]][row[3]] = row[1]
except IndexError:
None
print(report_dict)
Result:
report_dict = { 'abc': {'qwe':['asd','123'], 'ewq':['zxc']}, 'bcd' : {'qwe':['asd'], 'ewq':['zxc']} …..}
Please note there are duplicate keys in the dataset.
you could do:
d = {}
for i in results:
if not d.get(i[0],0):
d[i[0]] = {}
if not d[i[0]].get(i[3],0):
d[i[0]][i[3]] = []
d[i[0]][i[3]].append(i[4])
d
{'abc': {'qwe': ['asd', '123'], 'ewq': ['zxc']}, 'bcd': {'ewq': ['zxc', 'zxc']}}
The following is a solution to your immediate question with tuples in the list:
from collections import defaultdict
report_dict = defaultdict(list)
# results = self.report_data(conn)
results = [["abc",123,1123,"qwe", "asd"],["abc",123,1123,"ewq","zxc"], ["bcd",123,1123,"ewq","zxc"], ["bcd",123,1123,"ewq","zxc"]]
for row in results:
try:
report_dict[row[0]].append((row[3], row[1]))
except IndexError:
None
print(report_dict)
Result: defaultdict(<class 'list'>, {'abc': [('qwe', 123), ('ewq', 123)], 'bcd': [('ewq', 123), ('ewq', 123)]})
you can also change it to a dictionaries in the list with the following line
report_dict[row[0]].append({row[3]: row[1]})
Result: defaultdict(<class 'list'>, {'abc': [{'qwe': 123}, {'ewq': 123}], 'bcd': [{'ewq': 123}, {'ewq': 123}]})

Create JSONL with Python

I can't figure out how to create JSONL using Python3.
test = [{'a': 'b'}, {'a': 'b'}, {'a': 'b'}]
with open("data.json", 'w') as f:
for item in test:
json.dump(item, f)
with open("data.json") as f:
for line in f:
// only 1 line here!
print(line)
// prints
{"a": "b"}{"a": "b"}{"a": "b"}
I've tried using indent option to dump but it appears to make no different and the separators option don't seem to be a great usecase. Not sure what I'm missing here?
Use .write with newline \n
Ex:
import json
test = [{'a': 'b'}, {'a': 'b'}, {'a': 'b'}]
with open("data.json", 'w') as f:
for item in test:
f.write(json.dumps(item) + "\n")
with open("data.json") as f:
for line in f:
print(line)

convert text file into dictionary -Python

I am given a .txt file which looks like this..
2:rain
3:odd
5:yes
6:go
I need to convert it into a dictionary.
This is what I have done so far.
words_dict = {}
file = open(filename, "r")
for word in file:
k, v = word.split(":")
words_dict[k.strip()] = v.strip()
file.close()
return words_dict
However, when i go and print the dictionary it does not match my expected output of {2: 'rain', 3: 'odd', 5: 'yes', 6: 'go'}
l="2:rain 3:odd 5:yes 6:go".split()
{x.split(":")[0]:x.split(":")[1] for x in l}
list_ = [x for x in open('text.txt').read().split()]
dict_ = {k: v for k, v in [x.split(':') for x in list_]}
# list_ = ['2:rain', '3:odd', '5:yes', '6:go']
# dict_ = {'2': 'rain', '3': 'odd', '5': 'yes', '6': 'go'}

Resources