Должен ли я использовать YAML или JSON для хранения данных Perl?

Я использую формат YAML с достаточным успехом в последние 6 месяцев или около того.

Тем не менее, чистая Perl-реализация парсера YAML довольно непроста для написания вручную читаемого файла и имеет (на мой взгляд) досадные причуды, такие как требование перехода на новую строку в конце файла. Это также гигантски медленно по сравнению с остальной частью моей программы.

Я обдумываю следующую эволюцию моего проекта и вместо этого рассматриваю возможность использования JSON (как оказалось, в основном строгого подмножества YAML). Но какой формат пользуется наибольшим вниманием и усилием в Perl?

Какой сегодня представляется лучшим долгосрочным форматом простого описания данных в Perl, YAML или JSON и почему?

7 ответов

Решение

YAML vs JSON - это что-то не очень понятное в Perl, и я признаю, что склоняюсь к этому. Я бы посоветовал, что любой из них привлечет к вам как можно больше внимания сообщества. Я бы принял решение, основываясь на различных плюсах и минусах форматов. Я разбил различные варианты сериализации данных следующим образом (я собираюсь добавить вики сообщества, чтобы люди могли добавить к нему):

YAML Pros

  • Дружелюбный человек, люди пишут базовый YAML, даже не подозревая об этом
  • WYSIWYG струны
  • Выразительный (имеет характер TMTOWDI)
  • Расширяемая система типов / метаданных
  • Perl-совместимые типы данных
  • портативный
  • Знакомый (большая часть встроенного и строкового синтаксиса выглядит как код Perl)
  • Хорошие реализации, если у вас есть компилятор (YAML::XS)
  • Хорошая способность сбрасывать данные Perl
  • Компактное использование экранного пространства (возможно, вы можете отформатировать в одну строку)

YAML Минусы

JSON Pros

  • Человек для чтения / записи
  • Маленькая спецификация
  • Хорошие реализации
  • портативный
  • Perlish синтаксис
  • YAML 1.2 - это расширенный набор JSON
  • Компактное использование экранного пространства
  • Перл дружественные типы данных
  • Многие вещи обрабатывают JSON

JSON Минусы

  • Строки не WYSIWYG
  • Нет расширяемости
  • Некоторые структуры Perl должны быть выражены ad-hoc (объекты и глобусы)
  • Недостаток выразительности

XML Pros

  • Широкое применение
  • Синтаксис знакомый веб-разработчикам
  • Большой корпус хороших модулей XML
  • Schemas
  • Технологии поиска и преобразования данных
  • портативный

XML минусы

  • Утомительно для людей, чтобы читать и писать
  • Структуры данных, чуждые Perl
  • Недостаток выразительности
  • Большая спецификация
  • Подробный

Perl/Data::Dumper Pros

  • Нет зависимостей
  • Удивительно компактный (с правильными флажками)
  • Perl дружественный
  • Может сбрасывать почти все (через DDS)
  • выразительный
  • Компактное использование экранного пространства
  • WYSIWYG струны
  • Знакомый

Perl / Data:: Минусы самосвала

  • Непереносимый (на другие языки)
  • Небезопасно (без героических мер)
  • Непостижимый для не-Perl программистов

Сохраняемые плюсы

  • Компактный? (нет номеров, чтобы подтвердить это)
  • Быстро? (нет номеров, чтобы подтвердить это)

Хранимые минусы

  • Человек враждебный
  • Несовместимо с сохраняемыми версиями
  • Непереносимый (на другие языки)

Как и в большинстве вещей, это зависит. Я думаю, если вы хотите скорость и совместимость (с другими языками), используйте JSON, в частности JSON::XS.

Если вы хотите что-то, что только когда-либо будет использоваться модулями Perl, придерживайтесь YAML. Гораздо чаще встречаются модули Perl в CPAN, которые поддерживают описание данных с помощью YAML или зависят от YAML, чем JSON.

Обратите внимание, что я не авторитет, и это мнение основано главным образом на догадках и догадках. В частности, я не профилировал JSON::XS против YAML:: XS. Если я оскорбительно невежественен, я могу только надеяться, что заставлю кого-то достаточно рассердиться, чтобы внести полезную информацию в обсуждение, поправив меня.

Все дело в удобочитаемости, если это ваша главная задача, выберите YAML:

YAML:

american:
  - Boston Red Sox
  - Detroit Tigers
  - New York Yankees
national:
  - New York Mets
  - Chicago Cubs
  - Atlanta Braves

JSON:

{
  "american": [
    "Boston Red Sox", 
    "Detroit Tigers", 
    "New York Yankees"
  ], 
  "national": [
    "New York Mets", 
    "Chicago Cubs", 
    "Atlanta Braves"
  ]
}

Чистая реализация Perl YAML (YAML модуль в отличие от YAML::SyckКажется, есть некоторые серьезные проблемы. Недавно я столкнулся с проблемами, когда он не мог обработать документы YAML с очень длинными строками (32 тыс. Символов или около того).

YAML может хранить и загружать благословенные переменные и делает это по умолчанию (фрагмент ниже был скопирован из *sepia-repl* буфер в Emacs):

I need user feedback!  Please send questions or comments to seano@cpan.org.
Sepia version 0.98.
Type ",h" for help, or ",q" to quit.
main @> use YAML
undef
main @> $foo = bless {}, 'asdf'
bless( {}, 'asdf' )
main @> $foo_dump = YAML::Dump $foo
'--- !!perl/hash:asdf {}
'
main @> YAML::Load $foo_dump
bless( {}, 'asdf' )

Это довольно страшно с точки зрения безопасности, потому что ненадежные данные могут быть использованы для вызова любого DESTROY метод, который был определен в вашем приложении - или любом из модулей, которые он использует.

Следующая короткая программа демонстрирует проблему:

#!/usr/bin/perl
use YAML;
use Data::Dumper;
package My::Namespace;
sub DESTROY {
    print Data::Dumper::Dumper \@_;
}
package main;
my $var = YAML::Load '--- !!perl/hash:My::Namespace
bar: 2
foo: 1
';

JSON не позволяет этого по умолчанию - возможно сериализовать Perl-объекты, но для этого вам нужно определить методы TO_JSON.

Если вы рассматриваете нотацию объектов JavaScript, почему бы не использовать "нотацию объектов Perl"?

JSON:

{"name": "bob", "parents": {"mother": "susan", "father": "bill"}, "nums": [1, 2, 3]}

Perl:

{name => "bob", parents => {mother => "susan", father => "bill"}, nums => [1, 2, 3]}

Я использую YAML для отслеживания состояния процессов, потому что я могу читать YML в середине процесса. Вам (технически) нужны полностью сформированные документы для чтения XML или JS. YAML удобен для отслеживания статуса, потому что вы можете записать множество мини-документов в файл. В противном случае я обычно использую XML или JS. Хорошая сводка плюсов и минусов выше, кстати.

Вы также можете рассмотреть возможность использования Storable. Скорее всего, вы получите очень хороший прирост скорости. Компромиссы:

  • сохраняемый формат является двоичным и не читаемым человеком, как JSON или YAML
  • Storable не является чистым модулем Perl (если это имеет значение)
Другие вопросы по тегам