Подтвердить что ты не робот

С++ 11 - уникальность типа

В С++ 11 я использую этот

typeid(T).name()

для моего собственного хеш-вычисления. Мне не нужно, чтобы результат был одинаковым между прогонами программы или компиляциями. Мне просто нужно, чтобы он был уникальным для типов. Я знаю, что он может возвращать одно и то же имя для разных типов, но обычно это с константами, указателями и т.д. В моем случае T - это только class XY, struct XX или производные типы.

В этом случае можно предположить, что T будет уникальным?

4b9b3361

Ответ 1

Вы должны использовать std::type_index для целей сопоставления.

Класс type_index - это класс оболочки вокруг std:: type_info объект, который может использоваться как индекс в ассоциативном и неупорядоченном ассоциативные контейнеры. Связь с объектом type_info поддерживается через указатель, поэтому type_index является CopyConstructible и CopyAssignable.

Ответ 2

std::type_info::name определяется реализацией, поэтому вы не должны полагаться на то, что он уникален для разных типов.

Так как вы делаете это для вычисления хэша, вы должны использовать std::type_info::hash_code. Хотя это не гарантирует, что значения будут уникальными, стандарт говорит, что реализации должны пытаться возвращать разные значения для разных типов. Пока ваша реализация хэш-карты имеет разумную обработку столкновений, этого вам должно быть достаточно.

Ответ 3

Как указано на cppreference:

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

Итак, нет, вы не можете. Вы ничего не можете принять на самом деле.

Хотя hash_code() дает вам:

size_t hash_code() const noexcept;

7 Возвраты: неопределенное значение, за исключением того, что в течение одного выполнения программы, он должен вернуть одно и то же значение для любых двух типов typeinfo объекты, которые сравниваются с равными.

8 Замечание: реализация должна возвращать разные значения для двух type_info, которые не сравниваются с равными.

Это означает, что hash_code() можно использовать для различения двух разных типов, только если operator== для type_info поддерживает это.

Ответ 4

Что вы могли бы сделать, это взять адрес члена.

class HashBase {
    virtual intptr_t get() = 0;
};

template <typename T>
class Hash : HashBase {
    static const int _addr = 0;
    intptr_t get() override { return reinterpret_cast<intptr_t>(&_addr); }
};