шаблон функции для сериализации перечислений - PullRequest
3 голосов
/ 19 апреля 2011

Я написал шаблон функции для сериализации перечислений в / из нашего потокового класса (да, я знаю boost :: serialization, но в моей ситуации это не вариант). Перечисления по договоренности в нашей компании сериализуются как int:

template<typename T>
Stream& operator<<( Stream& s, T const& value )
{
    s << ( int ) value;
}

template<typename T>
Stream& operator>>( Stream& s, T & value )
{
    int v;
    s >> v;
    value = (T) v;
}

Это простые шаблоны, и они прекрасно работают и в моих шаблонах функций для (де) сериализации вектора элементов перечисления. Я обеспокоен тем, что они являются слишком общими, то есть применяются к типам T, которые не enums, но могут быть преобразованы в int. Могу ли я улучшить шаблоны enum-сериализации (или, может быть, шаблоны vector-сериализации), чтобы убедиться, что они применяются только к векторам enum s?

1 Ответ

5 голосов
/ 19 апреля 2011

Здесь необходимо сделать два улучшения: не всегда сериализовать как int (не все перечисления), а как бы не был базовый тип.И, как ваш запрос, принимать только перечисления.

Последнее легко решается с помощью std::enable_if и std::is_enum:

typename std::enable_if<std::is_enum<T>::value, Stream&>::type
    operator<<( Stream& s, T const& value )

// and likewise for operator>>

А для первого выполните следующие действия внутриfunction:

Stream& operator<<( Stream& s, T const& value )
{
    typedef typename std::underlying_type<T>::type safe_type;
    s << static_cast<safe_type>(value);
}

// and likewise for operator>>

Для этого требуется C ++ 0x.

Если это не вариант, в Boost можно найти как enable_if, так и is_enum.Тем не менее, я думаю, вам нужно будет сделать underlying_type самостоятельно .(И, конечно, в худшем случае вы можете сделать все три самостоятельно, хотя, если я правильно помню, is_enum может быть болезненным.)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...