[python] 피클 또는 JSON?

dict키가 유형 str이고 값이 ints 인 작은 개체 를 디스크에 저장 한 다음 복구해야합니다 . 이 같은:

{'juanjo': 2, 'pedro':99, 'other': 333}

최선의 선택은 무엇이며 그 이유는 무엇입니까? pickle또는로 직렬화하십시오 simplejson.

Python 2.6을 사용하고 있습니다.



답변

상호 운용성 요구 사항이없고 (예 : Python에서 데이터를 사용하려는 경우) 바이너리 형식이 괜찮다면, 정말 빠른 Python 객체 직렬화를 제공 하는 cPickle 을 사용하십시오.

상호 운용성을 원하거나 텍스트 형식으로 데이터를 저장하려면 JSON (또는 제약 조건에 따라 다른 적절한 형식)을 사용하십시오.


답변

직렬화를 위해 피클보다 JSON을 선호합니다. Unpickling은 임의의 코드를 실행할 수 pickle있으며 프로그램간에 데이터를 전송하거나 세션간에 데이터를 저장하는 데 사용하는 것은 보안 허점입니다. JSON은 보안 허점을 도입하지 않고 표준화되어 있으므로 필요한 경우 다른 언어로 된 프로그램에서 데이터에 액세스 할 수 있습니다.


답변

몇 가지 차트를 통해 흥미로운 사실을 발견 할 수도 있습니다. http://kovshenin.com/archives/pickle-vs-json-which-is-faster/


답변

주로 속도와 공간에 관심이 있다면 cPickle이 JSON보다 빠르기 때문에 cPickle을 사용하십시오.

상호 운용성, 보안 및 / 또는 사람의 가독성에 더 관심이 있다면 JSON을 사용하십시오.


다른 답변에서 참조 된 테스트 결과는 2010 년에 기록되었으며 2016 년 cPickle 프로토콜 2를 사용한 업데이트 된 테스트 는 다음을 보여줍니다.

  • cPickle 3.8 배 빠른 로딩
  • cPickle 1.5 배 더 빠른 읽기
  • c 약간 더 작은 인코딩 선택

다른 답변에서 참조 된 Konstantin의 벤치 마크를 기반으로 하지만 pickle 대신 프로토콜 2와 함께 cPickle을 사용하고 simplejson 대신 json을 사용 하는 이 요점으로 직접 재현하십시오 ( json이 simplejson보다 빠르기 때문에 ).

wget https://gist.github.com/jdimatteo/af317ef24ccf1b3fa91f4399902bb534/raw/03e8dbab11b5605bc572bc117c8ac34cfa959a70/pickle_vs_json.py
python pickle_vs_json.py

괜찮은 2015 Xeon 프로세서에서 Python 2.7을 사용한 결과 :

Dir Entries Method  Time    Length

dump    10  JSON    0.017   1484510
load    10  JSON    0.375   -
dump    10  Pickle  0.011   1428790
load    10  Pickle  0.098   -
dump    20  JSON    0.036   2969020
load    20  JSON    1.498   -
dump    20  Pickle  0.022   2857580
load    20  Pickle  0.394   -
dump    50  JSON    0.079   7422550
load    50  JSON    9.485   -
dump    50  Pickle  0.055   7143950
load    50  Pickle  2.518   -
dump    100 JSON    0.165   14845100
load    100 JSON    37.730  -
dump    100 Pickle  0.107   14287900
load    100 Pickle  9.907   -

피클 프로토콜 3을 사용하는 Python 3.4는 더 빠릅니다.


답변

JSON 또는 피클? JSON 피클 은 어떻습니까 ! 사용할 수 있습니다 jsonpickle. 사용하기 쉽고 디스크의 파일은 JSON이기 때문에 읽을 수 있습니다.

http://jsonpickle.github.com/


답변

몇 가지 방법을 시도한 결과 덤프 방법의 프로토콜 인수를 다음과 같이 설정하여 cPickle을 사용하는 cPickle.dumps(obj, protocol=cPickle.HIGHEST_PROTOCOL)것이 가장 빠른 덤프 방법 이라는 것을 알았습니다 .

import msgpack
import json
import pickle
import timeit
import cPickle
import numpy as np

num_tests = 10

obj = np.random.normal(0.5, 1, [240, 320, 3])

command = 'pickle.dumps(obj)'
setup = 'from __main__ import pickle, obj'
result = timeit.timeit(command, setup=setup, number=num_tests)
print("pickle:  %f seconds" % result)

command = 'cPickle.dumps(obj)'
setup = 'from __main__ import cPickle, obj'
result = timeit.timeit(command, setup=setup, number=num_tests)
print("cPickle:   %f seconds" % result)


command = 'cPickle.dumps(obj, protocol=cPickle.HIGHEST_PROTOCOL)'
setup = 'from __main__ import cPickle, obj'
result = timeit.timeit(command, setup=setup, number=num_tests)
print("cPickle highest:   %f seconds" % result)

command = 'json.dumps(obj.tolist())'
setup = 'from __main__ import json, obj'
result = timeit.timeit(command, setup=setup, number=num_tests)
print("json:   %f seconds" % result)


command = 'msgpack.packb(obj.tolist())'
setup = 'from __main__ import msgpack, obj'
result = timeit.timeit(command, setup=setup, number=num_tests)
print("msgpack:   %f seconds" % result)

산출:

pickle         :   0.847938 seconds
cPickle        :   0.810384 seconds
cPickle highest:   0.004283 seconds
json           :   1.769215 seconds
msgpack        :   0.270886 seconds


답변

개인적으로 저는 데이터가 사람이 읽을 수 있기 때문에 일반적으로 JSON을 선호합니다 . 확실히, JSON이 취할 수없는 것을 직렬화해야한다면 pickle을 사용하십시오.

그러나 대부분의 데이터 저장소에서는 이상한 것을 직렬화 할 필요가 없으며 JSON은 훨씬 더 쉽고 항상 텍스트 편집기에서 열어 데이터를 직접 확인할 수 있습니다.

속도는 좋지만 대부분의 데이터 세트에서 그 차이는 미미합니다. 파이썬은 일반적으로 어쨌든 너무 빠르지 않습니다.