Вы не можете предоставить это напрямую, но вы можете использовать any
в качестве базового типа ... хотя для указателей это бессмысленно (ах!)
struct any {
std::type_info const& _info;
void* _address;
};
И шаблонный конструктор:
template <typename T>
any::any(T* t):
_info(typeid(*t)),
_address(dynamic_cast<void*>(t))
{
}
Это, в основном, boost::any
.
Теперь нам нужно «дополнить» его нашим механизмом сравнения.
Для этого мы «захватим» реализацию std::less
.
typedef bool (*Comparer)(void*,void*);
template <typename T>
bool compare(void* lhs, void* rhs) const {
return std::less<T>()(*reinterpret_cast<T*>(lhs), *reinterpret_cast<T*>(rhs));
}
template <typename T>
Comparer make_comparer(T*) { return compare<T>; }
И дополнить конструктор any
.
struct any {
std::type_info const& _info;
void* _address;
Comparer _comparer;
};
template <typename T>
any::any(T* t):
_info(typeid(*t)),
_address(dynamic_cast<void*>(t)),
_comparer(make_comparer(t))
{
}
Затем мы предоставили специализацию less
(или operator<
)
bool operator<(any const& lhs, any const& rhs) {
if (lhs._info.before(rhs._info)) { return true; }
if (rhs._info.before(lhs._info)) { return false; }
return (*lhs._comparer)(lhs._address, rhs._address);
}
Примечание: инкапсуляция и т.д ... оставлены читателю в качестве упражнения