web-dev-qa-db-fra.com

Conversion du dictionnaire Python en tableau JSON

Actuellement, j'ai ce dictionnaire imprimé avec pprint:

{'AlarmExTempHum': '\x00\x00\x00\x00\x00\x00\x00\x00',  
'AlarmIn': 0,  
'AlarmOut': '\x00\x00',  
'AlarmRain': 0,  
'AlarmSoilLeaf': '\x00\x00\x00\x00',  
'BarTrend': 60,  
'BatteryStatus': 0,  
'BatteryVolts': 4.751953125,  
'CRC': 55003,
'EOL': '\n\r',
'ETDay': 0,
'ETMonth': 0,
'ETYear': 0,
'ExtraHum1': None,
'ExtraHum2': None,
'ExtraHum3': None,
'ExtraHum4': None,
'ExtraHum5': None,
'ExtraHum6': None,
'ExtraHum7': None,
'ExtraTemp1': None,
'ExtraTemp2': None,
'ExtraTemp3': None,
'ExtraTemp4': None,
'ExtraTemp5': None,
'ExtraTemp6': None,
'ExtraTemp7': None,
'ForecastIcon': 2,
'ForecastRuleNo': 122,
'HumIn': 31,
'HumOut': 94,
'LOO': 'LOO',
'LeafTemps': '\xff\xff\xff\xff',
'LeafWetness': '\xff\xff\xff\x00',
'NextRec': 37,
'PacketType': 0,
'Pressure': 995.9363359295631,
'RainDay': 0.0,
'RainMonth': 0.0,
'RainRate': 0.0,
'RainStorm': 0.0,
'RainYear': 2.8,
'SoilMoist': '\xff\xff\xff\xff',
'SoilTemps': '\xff\xff\xff\xff',
'SolarRad': None,
'StormStartDate': '2127-15-31',
'SunRise': 849,
'SunSet': 1611,
'TempIn': 21.38888888888889,
'TempOut': 0.8888888888888897,
'UV': None,
'WindDir': 219,
'WindSpeed': 3.6,
'WindSpeed10Min': 3.6}

Quand je fais ça:

import json
d = (my dictionary above)
jsonarray = json.dumps(d)

Je reçois cette erreur: 'utf8' codec can't decode byte 0xff in position 0: invalid start byte

93
HyperDevil

Si vous êtes prêt à utiliser des symboles non imprimables dans votre JSON, ajoutez ensuite ensure_ascii=False à dumps call.

>>> json.dumps(your_data, ensure_ascii=False)

Si ensure_ascii est faux, alors la valeur renvoyée sera une instance de unicode soumise à des règles normales Python str à unicode règles de coercition au lieu d'être échappée. un ASCII str.

162
kmerenkov

verify_ascii = False ne reporte vraiment la question qu'au stade de décodage:

>>> dict2 = {'LeafTemps': '\xff\xff\xff\xff',}
>>> json1 = json.dumps(dict2, ensure_ascii=False)
>>> print(json1)
{"LeafTemps": "����"}
>>> json.loads(json1)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/lib/python2.7/json/__init__.py", line 328, in loads
    return _default_decoder.decode(s)
  File "/usr/lib/python2.7/json/decoder.py", line 365, in decode
    obj, end = self.raw_decode(s, idx=_w(s, 0).end())
  File "/usr/lib/python2.7/json/decoder.py", line 381, in raw_decode
    obj, end = self.scan_once(s, idx)
UnicodeDecodeError: 'utf8' codec can't decode byte 0xff in position 0: invalid start byte

En fin de compte, vous ne pouvez pas stocker d'octets bruts dans un document JSON. Vous devrez donc utiliser un moyen de coder sans ambiguïté une séquence d'octets arbitraires sous la forme d'une chaîne ASCII, telle que base64.

>>> import json
>>> from base64 import b64encode, b64decode
>>> my_dict = {'LeafTemps': '\xff\xff\xff\xff',} 
>>> my_dict['LeafTemps'] = b64encode(my_dict['LeafTemps'])
>>> json.dumps(my_dict)
'{"LeafTemps": "/////w=="}'
>>> json.loads(json.dumps(my_dict))
{u'LeafTemps': u'/////w=='}
>>> new_dict = json.loads(json.dumps(my_dict))
>>> new_dict['LeafTemps'] = b64decode(new_dict['LeafTemps'])
>>> print new_dict
{u'LeafTemps': '\xff\xff\xff\xff'}
17
rkday

Si vous utilisez Python 2, n'oubliez pas d'ajouter le commentaire de codage de fichier UTF-8 sur la première ligne de votre script.

# -*- coding: UTF-8 -*-

Cela résoudra certains problèmes Unicode et vous simplifiera la vie.

8
justice

Une solution possible que j'utilise est d'utiliser python3. Il semble résoudre de nombreux problèmes UTF.

Désolé pour la réponse tardive, mais cela pourrait aider les gens dans le futur.

Par exemple,

#!/usr/bin/env python3
import json
# your code follows
2
Ralph Yozzo