Языковая интеграция
Возможно, я здесь меньшинство, но, похоже, за всю мою академическую / профессиональную карьеру меня учили на разных языках. В течение этого времени в центре внимания были синтаксис и парадигмы программирования, но мы ни разу не учили нас об интеграции систем, написанных на разных языках, и о том, как правильно принимать это решение.
Теперь для записи, я не говорю о каноническом веб-стеке или более новых, более сексуальных, дружественных для JVM языках. Мне интересно, есть ли "известные ресурсы", где я мог бы узнать о процессах принятия решений за языками связывания, такими как, например, Java и C++.
Конечно, на ум приходят такие инструменты, как XML, JSON и XMPP. С другой стороны, я видел системы, связывающие Java и C++ с использованием сериализации. Я не ищу единого решения для всех. Мне больше интересно узнать о различных решениях и о том, как я должен поступать, принимая такие решения.
Приношу свои извинения, если это слишком широко для этого форума, но, по крайней мере, я не прошу людей исправить или переписать мой испорченный код;)
5 ответов
Я могу придумать четыре разные модели:
Встроить динамический язык в приложение, которое в основном написано на более "системном" языке, например, Lua, Python или Javascript, встроенном в приложение Java, C++ или C#. Это используется в основном для сценариев / настройки компонента приложения. Это будет достигнуто путем предоставления некоторых типов данных хост-приложений в формате, который может использовать динамический язык.
Написать собственные (или C# или Java) расширения для языка с проблемами производительности. Python и Ruby имеют много таких расширений. Это отличается от вышеизложенного тем, что динамический язык является основой. Это достигается написанием собственных библиотек (или оболочки вокруг других собственных библиотек) для соответствия соглашениям о вызовах языка клиента. Это также та же общая структура при смешивании ассемблера с C в системном коде.
Запускайте приложения в разных адресных пространствах и общайтесь через сокеты или каналы. В данном случае это просто совпадение, что приложения работают на одной машине вообще - они могут с тем же успехом общаться по сети.
Разработайте приложение, используя несколько языков, использующих одну платформу и соглашения о вызовах. Например, Java и Scala могут свободно смешиваться.
Безопасное решение - это многопроцессорное решение, где каждый язык работает в своем собственном адресном пространстве, и они взаимодействуют через сокеты или некоторую другую многопроцессорную абстракцию (например, кортежи Линды).
Если два языка работают в одном и том же адресном пространстве, то либо они должны быть спроектированы вместе на основе общей среды выполнения (как прекрасно работала Digital со своим семейством языков VAX VMS, и как Microsoft изо всех сил пыталась сделать с помощью Common Language Runtime для.NET) или один должен быть "ответственным". Есть много языков (OCaml, Standard ML, Haskell, Lua и, вероятно, также Perl, Ruby), которые прекрасно взаимодействуют с C, если они отвечают. Они не взаимодействуют друг с другом.
Обычно самой фундаментальной трудностью является автоматическое управление памятью ("управляемая куча"). Некоторая единица должна отвечать за то, когда безопасно возвращать мертвые объекты, и если два разных языка решат, что именно они должны ответить на этот вопрос, то возникнут отдельные процессы.
Lua - это язык сценариев, который очень хорошо интегрируется с C в одном и том же процессе. Он использует модель стека для преодоления несоответствия импеданса между двумя языками / средами выполнения. Реализация Lua имеет открытый исходный код и относительно компактна; так что это может быть хорошим кандидатом на учебу.
D-Bus является примером использования IPC. Его можно использовать для интеграции отдельных процессов, реализованных на разных языках. Он поддерживает асинхронный обмен сообщениями, а также синхронный вызов метода. Есть реализации D-Bus для Gtk, Qt, python и т.д...
Виртуальная машина Parrot - это виртуальная машина, предназначенная для взаимодействия языков.
Еще один подход - тот, который использует GLib (используется Gtk). Из руководства GObject:
Решение, используемое GLib, заключается в использовании библиотеки GType, которая содержит во время выполнения описание всех объектов, которыми манипулирует программист. Затем эта так называемая динамическая библиотека типа 1 используется специальным универсальным связующим кодом для автоматического преобразования параметров функций и соглашений о вызовах функций между различными доменами времени выполнения.
Немного расходятся в процессе принятия решений...
При построении системы вы разделяете ее на функционально независимые подсистемы. Теоретически для каждой подсистемы вы должны выяснить, на какой основе вы ее построите. Аспекты, которые имеют значение: * какая инфраструктура лучше всего соответствует функциональности подсистемы * какие платформы удобны для ваших разработчиков * будущая поддержка: что, если поставщик инфраструктуры перестает ее поддерживать (как MS почти сделал с неуправляемым C++) *
Когда система становится неоднородной, самое время подумать о кроссовке внутри подсистемы. Это также может рассматриваться как отдельная подсистема и может быть построено на нескольких протоколах межпроцессного взаимодействия, таких как MPI, каналы, или что-то домашнее.