Генерация временного кода в D - PullRequest
10 голосов
/ 10 сентября 2010

В настоящее время я изучаю D, и одна из вещей, которые меня интересуют, заключается в том, может ли D дублировать возможности генерации кода языков JVM.

Вот сценарий: У меня есть объект, и я хочу сгенерировать строку на основе этого объекта, которая дает его имя и все его поля. В Java / Scala я мог бы просто использовать отражение, но предположим, что скорость - это проблема. Я мог бы использовать библиотеку генерации байт-кода, чтобы динамически генерировать и компилировать класс, который делает это без отражения. Реализация будет разбита на итерацию по полям объекта и получение его имени через рекурсию и использование этой информации для динамической генерации Java (или байт-кода), который напрямую обращается к полям.

Если вам не нравится этот сценарий, потому что он слабый и / или нереалистичный, еще один, который может быть более реалистичным, - это оптимизированная сериализация объектов.

Я видел примеры, когда оценка D во время компиляции и / или шаблонное метапрограммирование используются для таких вещей, как предварительный расчет последовательности Фибоначчи во время компиляции и других рекурсивных алгоритмов, но есть ли способ сделать такие вещи, используя только язык и компилятор, или вам нужно разработать отдельный генератор кода и запустить его перед компилятором, чтобы получить такую ​​функциональность?

Ответы [ 2 ]

6 голосов
/ 10 сентября 2010

Мало того, что это может быть сделано, это практически сделано для вас в D2. Все, что вам нужно, это небольшой миксин, чтобы превратить их из функций времени компиляции в функции времени выполнения.

  • Для имени класса все, что вам нужно сделать, это оценить typeof(this).stringof внутри области видимости класса.

  • Для получения списка всех полей попробуйте __traits(allMembers, typeof(this)), а затем отфильтруйте материал, который не является полем (здесь будет полезно std.traits).

5 голосов
/ 10 сентября 2010

Строковые миксины могут получить доступ к пространству имен, в которое они смешаны. Это включает this.tupleof, который можно использовать для итерации полей класса. Шаблон сериализации может воспользоваться этим или иным образом заставить пользователя указать поля для сериализации вручную; то есть. class Class : ISerializable { int foo; Forble bar; mixin(genSerialize("foo, bar")); ... }

...