2013-08-22 12 views
1

У меня есть список уродливых объектов JSON в текстовом файле, по одному в каждой строке. Я бы хотел, чтобы они хорошо печатали и отправляли результаты в файл.Как эффективно печатать список объектов JSON?

Моя попытка использовать питона версию командной строки json.tool:

parallel python -mjson.tool < jsonList 

Однако, что-то, кажется, идет не так в разборе этого JSON, а json.tool питона пытается открыть его как множественные аргументы и, таким образом бросает:

IOError: [Errno 2] нет такого файла или каталога: {содержимое строки, содержащие одиночные кавычки, пробелы, двойные кавычки}

Как я могу заставить это относиться к каждой линии -сепарализованный объект как один аргумент модуль? Открытие файла непосредственно на python и его обработка серийно является неэффективным решением, потому что файл огромен. Попытка сделать это привязывает процессор.

+0

jsonList файл? –

+0

Да. Текстовый файл в несколько GB. – argentage

ответ

1

GNU Parallel по умолчанию помещает ввод в качестве аргументов в командной строке. Так что вы делаете:

python -mjson.tool \[\"cheese\",\ \{\"cake\":\[\"coke\",\ null,\ 160,\ 2\]\}\] 

Но что вы хотите:

echo \[\"cheese\",\ \{\"cake\":\[\"coke\",\ null,\ 160,\ 2\]\}\] | python -mjson.tool 

GNU Parallel можно сделать с --pipe -n1:

parallel -N1 --pipe python -mjson.tool < jsonList 

10 секунд установки:

wget -O - pi.dk/3 | bash 

Смотреть видеоролик для быстрого ввода : https://www.youtube.com/playlist?list=PL284C9FF2488BC6D1 или по адресу

Пройдитесь по учебнику (man parallel_tutorial).Вы в командной строке с любовью к вам.

+0

Это то, что я думал, что хочу, хотя это было медленнее, чем я думал, что это будет! – argentage

1

Ну, у модуля json уже есть что-то похожее на то, что вы имеете в виду.

>>> import json 
>>> 
>>> my_json = '["cheese", {"cake":["coke", null, 160, 2]}]' 
>>> parsed = json.loads(my_json) 
>>> print json.dumps(parsed, indent=4, sort_keys=True) 
[ 
    "cheese", 
    { 
     "cake": [ 
      "coke", 
      null, 
      160, 
      2 
     ] 
    } 
] 

И вы можете просто ввести my_json из текстового файла, используя open в режиме r.

+0

Я избегал использования команды open непосредственно в скрипте python, потому что я не знаю, что будет делать python с текстовым файлом 2 ГБ. – argentage

+0

Посмотрите @ this: http://stackoverflow.com/questions/7134338/max-size-of-a-file-python-can-open –

+1

@airza: «открыть» файл не означает «загрузить всю файл в память ". Просто повторите его по строке ('for line in file') и выполните преобразование, как показано. Он будет работать независимо от того, насколько большой файл. – georg

0

две проблемы с моим подходом, который я в конце концов решил:

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

По умолчанию json.tool выполняет наивную реализацию, но каким-то образом вводит в заблуждение количество входящих аргументов.

Я написал:

import sys 
import json 
for i in sys.argv[1:]: 
    o = json.loads(i) 
    json.dump(o, sys.stdout, indent=4, separators=(',',': ')) 

Тогда назвал это так:

параллельно -n 500 питон fastProcess.py < filein> prettyfileout

Я не совсем уверен, оптимальный значение n, но сценарий на 4-5 раз быстрее в режиме настенных часов, чем наивная реализация из-за возможности использования нескольких ядер.

Смежные вопросы