В чем разница между модулями json и simplejson Python?

Я видел много проектов, используя simplejson модуль вместо json из стандартной библиотеки. Кроме того, существует множество различных модулей simplejson. Зачем использовать эти альтернативы, а не одну в стандартной библиотеке?

Ответ 1

json simplejson, добавлен в stdlib. Но поскольку json был добавлен в 2.6, simplejson имеет преимущество в работе над более версиями Python (2.4+).

simplejson также обновляется чаще, чем Python, поэтому, если вам нужна (или нужна) последняя версия, лучше всего использовать simplejson, если это возможно.

Хорошей практикой, на мой взгляд, является использование того или другого в качестве резерва.

try: import simplejson as json
except ImportError: import json

Ответ 2

Я не согласен с другими ответами: встроенная библиотека json (в Python 2.7) не обязательно медленнее, чем simplejson. У этого также нет эта неприятная ошибка unicode.

Вот простой тест:

import json
import simplejson
from timeit import repeat

NUMBER = 100000
REPEAT = 10

def compare_json_and_simplejson(data):
    """Compare json and simplejson - dumps and loads"""
    compare_json_and_simplejson.data = data
    compare_json_and_simplejson.dump = json.dumps(data)
    assert json.dumps(data) == simplejson.dumps(data)
    result = min(repeat("json.dumps(compare_json_and_simplejson.data)", "from __main__ import json, compare_json_and_simplejson", 
                 repeat = REPEAT, number = NUMBER))
    print "      json dumps {} seconds".format(result)
    result = min(repeat("simplejson.dumps(compare_json_and_simplejson.data)", "from __main__ import simplejson, compare_json_and_simplejson", 
                 repeat = REPEAT, number = NUMBER))
    print "simplejson dumps {} seconds".format(result)
    assert json.loads(compare_json_and_simplejson.dump) == data
    result = min(repeat("json.loads(compare_json_and_simplejson.dump)", "from __main__ import json, compare_json_and_simplejson", 
                 repeat = REPEAT, number = NUMBER))
    print "      json loads {} seconds".format(result)
    result = min(repeat("simplejson.loads(compare_json_and_simplejson.dump)", "from __main__ import simplejson, compare_json_and_simplejson", 
                 repeat = REPEAT, number = NUMBER))
    print "simplejson loads {} seconds".format(result)


print "Complex real world data:" 
COMPLEX_DATA = {'status': 1, 'timestamp': 1362323499.23, 'site_code': 'testing123', 'remote_address': '212.179.220.18', 'input_text': u'ny monday for less than \u20aa123', 'locale_value': 'UK', 'eva_version': 'v1.0.3286', 'message': 'Successful Parse', 'muuid1': '11e2-8414-a5e9e0fd-95a6-12313913cc26', 'api_reply': {"api_reply": {"Money": {"Currency": "ILS", "Amount": "123", "Restriction": "Less"}, "ProcessedText": "ny monday for less than \\u20aa123", "Locations": [{"Index": 0, "Derived From": "Default", "Home": "Default", "Departure": {"Date": "2013-03-04"}, "Next": 10}, {"Arrival": {"Date": "2013-03-04", "Calculated": True}, "Index": 10, "All Airports Code": "NYC", "Airports": "EWR,JFK,LGA,PHL", "Name": "New York City, New York, United States (GID=5128581)", "Latitude": 40.71427, "Country": "US", "Type": "City", "Geoid": 5128581, "Longitude": -74.00597}]}}}
compare_json_and_simplejson(COMPLEX_DATA)
print "\nSimple data:"
SIMPLE_DATA = [1, 2, 3, "asasd", {'a':'b'}]
compare_json_and_simplejson(SIMPLE_DATA)

И результаты моей системы (Python 2.7.4, Linux 64-bit):

Сложные данные реального мира:
      json dumps 1.56666707993 секунды
simplejson dumps 2.25638604164 секунды
      json load 2.71256899834 секунды
simplejson load 1.29233884811 секунд

Простые данные:
      json dumps 0.370109081268 секунд
спейсы простого пользователя 0.574181079865 секунды
      json load 0.422876119614 секунды
simplejson load 0.270955085754 секунды

Для сброса, json быстрее, чем simplejson. Для загрузки simplejson выполняется быстрее.

Поскольку в настоящее время я создаю веб-службу, dumps() более важен, и использование стандартной библиотеки всегда предпочтительнее.

Кроме того, cjson не обновлялся за последние 4 года, поэтому я бы не стал его трогать.

Ответ 3

Все эти ответы не очень полезны, потому что они чувствительны к времени.

После самостоятельного исследования я обнаружил, что simplejson действительно быстрее, чем встроенный, if, который вы обновляете до последней версии.

pip/easy_install хотел установить 2.3.2 на ubuntu 12.04, но после выяснения последней версии simplejson на самом деле 3.3.0, поэтому я обновил ее и повторил тесты времени.

  • simplejson примерно в 3 раза быстрее встроенного json при загрузке
  • simplejson примерно на 30% быстрее, чем встроенный json на дампах

Отказ от ответственности:

Вышеуказанные утверждения приведены в python-2.7.3 и simplejson 3.3.0 (с ускорением c) И чтобы убедиться, что мой ответ также не чувствителен к времени, вы должны запустить свои собственные тесты, так как он сильно варьируется между версиями; нет простого ответа, который не зависит от времени.

Как узнать, включены ли ускорения C в simplejson:

import simplejson
# If this is True, then c speedups are enabled.
print bool(getattr(simplejson, '_speedups', False))

UPDATE: Недавно я встретил библиотеку под названием ujson, которая выполняет ~ 3 раза быстрее, чем simplejson с некоторыми базовыми тестами.

Ответ 4

Я сравнивал json, simplejson и cjson.

  • cjson самый быстрый
  • simplejson почти на одном уровне с cjson
  • json примерно в 10 раз медленнее, чем simplejson

http://pastie.org/1507411:

$ python test_serialization_speed.py 
--------------------
   Encoding Tests
--------------------
Encoding: 100000 x {'m': 'asdsasdqwqw', 't': 3}
[      json] 1.12385 seconds for 100000 runs. avg: 0.011239ms
[simplejson] 0.44356 seconds for 100000 runs. avg: 0.004436ms
[     cjson] 0.09593 seconds for 100000 runs. avg: 0.000959ms

Encoding: 10000 x {'m': [['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19], ['0', 1, '2', 3, '4', 5, '6', 7, '8', 9, '10', 11, '12', 13, '14', 15, '16', 17, '18', 19]], 't': 3}
[      json] 7.76628 seconds for 10000 runs. avg: 0.776628ms
[simplejson] 0.51179 seconds for 10000 runs. avg: 0.051179ms
[     cjson] 0.44362 seconds for 10000 runs. avg: 0.044362ms

--------------------
   Decoding Tests
--------------------
Decoding: 100000 x {"m": "asdsasdqwqw", "t": 3}
[      json] 3.32861 seconds for 100000 runs. avg: 0.033286ms
[simplejson] 0.37164 seconds for 100000 runs. avg: 0.003716ms
[     cjson] 0.03893 seconds for 100000 runs. avg: 0.000389ms

Decoding: 10000 x {"m": [["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19], ["0", 1, "2", 3, "4", 5, "6", 7, "8", 9, "10", 11, "12", 13, "14", 15, "16", 17, "18", 19]], "t": 3}
[      json] 37.26270 seconds for 10000 runs. avg: 3.726270ms
[simplejson] 0.56643 seconds for 10000 runs. avg: 0.056643ms
[     cjson] 0.33007 seconds for 10000 runs. avg: 0.033007ms

Ответ 5

Несовместимость API, которую я обнаружил, с Python 2.7 vs simplejson 3.3.1 заключается в том, выводит ли вывод объекты str или unicode. например.

>>> from json import JSONDecoder
>>> jd = JSONDecoder()
>>> jd.decode("""{ "a":"b" }""")
{u'a': u'b'}

против

>>> from simplejson import JSONDecoder
>>> jd = JSONDecoder()
>>> jd.decode("""{ "a":"b" }""")
{'a': 'b'}

Если предпочтение заключается в использовании simplejson, то это можно устранить, принудительно введя строку аргумента в unicode, как в:

>>> from simplejson import JSONDecoder
>>> jd = JSONDecoder()
>>> jd.decode(unicode("""{ "a":"b" }""", "utf-8"))
{u'a': u'b'}

Принуждение требует знания исходной кодировки, например:

>>> jd.decode(unicode("""{ "a": "ξηθννββωφρες" }"""))
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
UnicodeDecodeError: 'ascii' codec can't decode byte 0xce in position 8: ordinal not in range(128)

Это не будет исправлено проблема 40

Ответ 6

Встроенный модуль json включен в Python 2.6. Любые проекты, поддерживающие версии Python < 2.6 необходимо иметь резервную копию. Во многих случаях этот резерв равен simplejson.

Ответ 7

Еще одна причина, по которой проекты используют simplejson, заключается в том, что встроенный json первоначально не включал свои ускорители C, поэтому разница в производительности была заметна.

Ответ 8

Здесь (теперь устаревшее) сравнение библиотек Python json:

Сравнение модулей JSON для Python (ссылка на архив)

Независимо от результатов этого сравнения, вы должны использовать стандартную библиотеку json, если вы находитесь на Python 2.6. И.. может также просто использовать simplejson в противном случае.

Ответ 9

модуль simplejson просто в 1,5 раза быстрее, чем json (на моем компьютере, с simplejson 2.1.1 и Python 2.7 x86).

Если вы хотите, вы можете попробовать тест: http://abral.altervista.org/jsonpickle-bench.zip На моем компьютере simplejson быстрее, чем cPickle. Я также хотел бы узнать ваши тесты!

Возможно, как сказал Coady, разница между simplejson и json заключается в том, что simplejson включает _speedups.c. Итак, почему разработчики python не используют simplejson?

Ответ 10

Некоторые значения сериализуются по-разному между simplejson и json.

В частности, экземпляры collections.namedtuple сериализуются как массивы json, а как объекты simplejson. Вы можете переопределить это поведение, передав namedtuple_as_object=False в simplejson.dump, но по умолчанию поведение не соответствует.

>>> import collections, simplejson, json
>>> TupleClass = collections.namedtuple("TupleClass", ("a", "b"))
>>> value = TupleClass(1, 2)
>>> json.dumps(value)
'[1, 2]'
>>> simplejson.dumps(value)
'{"a": 1, "b": 2}'
>>> simplejson.dumps(value, namedtuple_as_object=False)
'[1, 2]'

Ответ 11

Я столкнулся с этим вопросом, поскольку я искал установку simplejson для Python 2.6. Мне нужно было использовать "object_pairs_hook" для json.load(), чтобы загрузить json файл в качестве OrderedDict. Будучи знакомым с более поздними версиями Python, я не понимал, что модуль json для Python 2.6 не включает "object_pairs_hook", поэтому мне пришлось установить simplejson для этой цели. Из личного опыта именно поэтому я использую simplejson в отличие от стандартного модуля json.

Ответ 12

В python3, если у вас есть строка b'bytes', с json вам нужно .decode() содержимое, прежде чем вы сможете загрузить его. simplejson позаботится об этом, поэтому вы можете просто сделать simplejson.loads(byte_string).