根据is_integer转换为int或float

时间:2011-01-14 11:03:47

标签: c++ templates typedef

我有一些类型T,在某些情况下它可能是,例如char,但我想输出其整数值,而不是字符。为此,有以下内容:

typedef ( std::numeric_limits< T >::is_integer ? int : float ) FormatType;
os << static_cast< FormatType >( t );

然而,这无法编译,说明“error C2275: 'int' : illegal use of this type as an expression”。使用int添加floattypename前缀并不能解决问题。我在这里缺少什么?

我认为以下内容相同,有效:

if( std::numeric_limits< T >::is_integer )
{
    os << static_cast< int >( t );
}
else
{
    os << static_cast< float >( t );
}

3 个答案:

答案 0 :(得分:3)

  

我在这里缺少什么?

您正在尝试将类型用作表达式。 C ++根本不允许这样做。您可以通过元编程使用所谓的“编译时if”。例如,我相信Boost提供以下内容:

typedef if_<std::numeric_limits< T >::is_integer, int, double>::type FormatType;

os << static_cast< FormatType >( t );

另一方面,你的第二个解决方案效果很好,编译器会发现其中一个分支永远不会是真的,并且消除它。因此在两种情况下性能都是相同的(事实上,应该生成完全相同的代码)。

答案 1 :(得分:2)

尝试使用积分促销:

os << +t;

对于整数类型,您将获得int,如果是一个类型,则为原始浮点类型。

答案 2 :(得分:0)

gcc接受它,不确定其他人:

template<bool Expression, typename TrueResult, typename FalseResult>
  class conditional_type;

template<typename TrueResult, typename FalseResult>
class conditional_type<1, TrueResult, FalseResult> {
public:
    typedef TrueResult R;
};

template<typename TrueResult, typename FalseResult>
class conditional_type<0, TrueResult, FalseResult> {
public:
    typedef FalseResult R;
};

typedef conditional_type<std::numeric_limits<T>::is_integer,int,float>::R FormatType;