2012-03-10 3 views
4

Я искал способ получить заказ по типам во время компиляции. Это было бы полезно, например, для реализации (эффективных) наборов типов времени компиляции.Сортировка времени компиляции по типам

Одним из очевидных способов сделать это было бы, если бы был способ сопоставить каждый тип с уникальным целым числом. Ответ на previous question по этой теме лаконично захватывает, почему это трудно, и кажется, что было бы в равной степени применим к любому другому способу пытаться получить заказ:

компилятора не имеют возможностей узнать все единицы компиляции и компоновщик не имеет понятия типа

Действительно, задача компилятора будет значительной: он должен убедиться в том, что в любом вызове, для любого исходного файла, он возвращает то же число для данного типа/он возвращает одинаковое упорядочение между любыми двумя заданными типами, но в то же время универсальный тип типов открыт и не знает никаких типов за пределами текущего файла. Жесткая проблема.

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

  • Если два типа имеют одинаковое имя, то они одного типа.

  • Если два типа одного типа, то либо они имеют одно и то же имя, либо они являются typedefs для друг друга. Компилятор имеет полное знание typedefs.

Имена - это строки, а строки имеют порядок. Поэтому, если у меня все будет правильно, вы можете определить глобально согласованный порядок по типам на основе их имен. Более конкретно, упорядочение между любыми двумя типами будет упорядочением между именами типов с полностью разрешенными typedefs. (Наличие типа по-разному отличается от его typedefs будет проблематичным.)

Конечно, стандартный C++ не имеет средств для получения имен типов.

Мои вопросы:

  • Есть ли у меня что-то не так? Существуют ли какие-либо причины, по которым теоретически это не будет работать?

  • Есть ли какие-либо компиляторы, которые дают вам доступ к именам типов (и в идеале их формам, разрешенным для typedef) во время компиляции в качестве расширения языка?

  • Есть ли другой способ, которым это можно было бы сделать? Есть ли компиляторы, которые делают?

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

+2

Я подозреваю, что вы используете неправильный язык программирования. –

+0

(И, FWIW, я думаю, что ваша группировка вопросов, вероятно, прекрасна в этом случае. Они плотно последовательны.) –

+0

«Конечно, стандартный C++ не имеет средств для поиска имен типов». - http://en.wikipedia.org/wiki/Typeid – FailedDev

ответ

1

полное имя типа должно быть уникальным по всей программе

Но, конечно, это только справедливо, если вы считаете, раздельные анонимные пространства имен в разных единицах трансляции, чтобы иметь разные имена в некотором смысле, и иметь какой-то способ выяснить, что они собой представляют.

Единственный смысл, в котором я знаю, что у них действительно есть разные имена, - это искаженные символы линкера; вы может (в зависимости от компилятора) иметь возможность получить это от type_info::name(), но это не гарантируется, ограничено типами с RTTI, и в любом случае не представляется объявленным как constexpr, поэтому вы не можете использовать значение во время компиляции.

У заказа, произведенного type_info::before(), естественно, те же ограничения.

Из интереса, чего вы пытаетесь достичь при заказе типа компиляции?

+0

Анонимные пространства имен! Очень хорошая точка. Я забыл о них. Обратите внимание, что функция полностью квалифицированных имен в моем вопросе не обязательно должна раскрывать их напрямую, но (гипотетически) как механизм для реализации последовательного упорядочения времени компиляции по типам. С этой целью (если я правильно думаю) почти не имеет значения, где в упорядочивании мы ставим их, если это согласовано. Что касается type_info :: name(), сам оператор typeid не является constexpr, так что это не приводит нас к очень далеко. – glaebhoerl

+0

Что касается моего варианта использования: я хочу реализовать систему типов записей, где «метки полей» могут совместно использоваться между типами записей. Но порядок полей в записи не должен иметь значения. «Имена» меток полей представлены фиктивными типами. На практике вам приходится записывать их в том или ином порядке, но Record должен полностью взаимодействовать с Record . Таким образом, типы должны вести себя скорее как набор, чем список. А для реализации набора вы предпочитаете иметь оператор <(). Это возможно без, но лучше. – glaebhoerl

+0

(И для записи еще одна вещь, о которой я совсем забыл, - это type_info :: before(). Мой прыгающий пункт был больше тем, как GHC/Haskell реализует свой класс Typeable. Но если typeid и type_info :: before() были constexpr (есть ли причина, по которой можно реализовать их во время выполнения, но не будет во время компиляции?), которые в основном решат мое желание там.) – glaebhoerl

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