2014-01-07 2 views
2

Я хотел бы передать сложные данные из службы C++ в приложение Lua. Это общение происходит по сети. Для простоты и скорости в приложении Lua я предпочел бы отправлять литералы литералов Lua (без необходимости отдельного парсера) вместо XML или JSON или YAML или таких.Сериализация таблицы Lua из C++ (через JSON)

Хотя существуют такие вещи, как библиотеки C++, которые пишут JSON, я не могу найти существующую библиотеку C++ для создания сериализованного Lua. Моя идея состоит в том, чтобы использовать существующую библиотеку JSON для C++, а затем преобразовать строку в Lua.

Так, например, я хотел бы преобразовать эту строку:

{ 
    "hello":42, 
    "array":[1,2,{"more":false},null,true], 
    "worst":"still [null]: got it?" 
} 

в эту строку:

{ 
    ["hello"]=42, 
    ["array"]={1,2,{["more"]=false},nil,true}, 
    ["worst"]="still [null]: got it?" 
} 

Наивный replace_all превращающего в : к =, [] к {}, и null до nil уничтожит содержимое внутри строк. Как я могу выполнить это преобразование?

Чтобы избежать проблем с XY problem я включил свой конец мотивацию на вершине и в названии, в случае, если строка преобразование JSON-> Lua является неправильным выбором.

+1

Хм, не конвертировать содержимое внутри строк? Это не совсем-тривиально, но если вы можете это сделать, то это должно быть именно то, что вы описали, нет? Также на самом деле разбирать JSON от Lua IMHO не особо сложно. Быстрая версия LuaJSON с LPEG не обязательно будет медленнее, чем анализ фактического кода Lua, поэтому, если вы можете запустить этот сценарий, я думаю, что это более простой вариант. У меня лично не было проблем с этим (и в моем случае я использовал больше, чем просто источник данных на C++, поэтому JSON был логичным выбором). –

+1

* Однако, один момент, о котором я забыл, заключается в том, что при использовании таблиц Lua вы можете фактически использовать автоматическое преобразование в байт-код, который должен сделать это заметно быстрее. Это может быть обход OTOH с использованием BSON или других сжатых форматов JSON. –

+0

@BartekBanachewicz Возможно, я преждевременно оптимизирую, но мне трудно поверить, что LPEG LuaJSON находится где-то рядом так же быстро, как 'local t = loadstring ('return' ..json)()' – Phrogz

ответ

2

Я бы назвал это Lua -format serializing библиотекой. Вы можете выбрать free software Json C++ library (например, jsoncpp или libjson) и легко адаптировать свой код (в свой Lua-формат).

Конечно, вы должны подчиняться лицензии этой библиотеки, и я настоятельно рекомендую вам сделать вашу библиотеку сериализации Lua-формата самой бесплатной программой, например. на github и/или freecode и/или sourceforge ...

Дело в том, что JSON (и, надеюсь, ваш формат Lua) достаточно прост, чтобы сделать довольно легко его синтаксический или печать ... Адаптация существующей библиотеки на формат, вероятно, более простой и, безусловно, быстрее, чем «пост-обработка» его выход ...

1

Хотя я не нашел его легко сегодня, я помню, что было около года назад обсуждение в списке Lua достоинств определения ограниченного подмножества литературных таблиц Lua, аналогичных JSON, получивших название «LSON» для обсуждения. IIRC, консенсус пришел к выводу о том, что не было достаточной выгоды для использования только с использованием стандартного легкого формата, такого как JSON, но я знаю, что были проведены некоторые эксперименты.

This Github Gist for lson.lua демонстрирует простой писатель и читатель LSON в чистом Lua. Писатель может быть преобразован в C или C++ только с умеренными усилиями, основанными на этом коде. Ключевая особенность этого кода заключается в том, что он обеспечивает некоторую защиту от циклических ссылок и против типов данных, которые могут храниться в таблицах, но которые не имеют разумного механизма для записи в качестве исходного кода (userdata и thread являются очень проблематичными для сериализации в любых форма). Разумеется, для данных, созданных как простые старые данные на C с только легкой структурой, в любом случае у вас не будет проблемных типов данных. Он также защищает от циклических ссылок. Если сериализовать списки или деревья из С, круговые ссылки могут быть невозможны по построению. Если нет, вам придется иметь дело с ними самостоятельно.

Обратите внимание, что использование собственного анализатора Lua потенциально может привести к проблемам безопасности. Самая вопиющая проблема заключается в том, что просто запись assert(loadstring('return '..Input))() позволяет импортированному текстовому доступу ко всей вашей текущей среде. Хотя существует некоторая защита в результате применения ключевого слова return вне текста ввода, это все равно не будет препятствовать умному использованию любых функций, которые могут быть вызваны из выражения. Для лучшей безопасности вы захотите прочитать около sandboxes и, возможно, даже примените некоторые умные трюки, чтобы ограничить скомпилированный байт-код перед тем, как его слепо исполнить.

Вопросы безопасности могут быть веским аргументом в пользу квалификации и использования анализатора JSON. Даже приложения javascipt часто предпочитают использовать парсеры JSON, а не просто позволить javascript-движку выполнять ненадежный контент.

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