提取模板类型的签名?
Extract signed-ness of template type?
下面的代码生成带有 -Wsign-conversion
的警告。它在 T digit = a % base
.
行生成警告
我想提取 T
的签名,然后将 base
转换为该签名以消除警告。
我试图避免专业化,因为那只会重复代码(唯一要改变的是 base
的签名)。我还试图避免将 base
强制转换为 T
,以防它是非 POD 类型,例如 Integer
(针对 longs
的缩减进行了优化)。
如何提取 T
的符号?
相关,代码库实际上是 C++98 和 C++03,因此它没有一些功能(如 Partial template specialization based on “signed-ness” of integer type? 中讨论的)。
template <class T>
std::string IntToString(T a, unsigned int base = 10)
{
if (a == 0)
return "0";
bool negate = false;
if (a < 0)
{
negate = true;
a = 0-a; // VC .NET does not like -a
}
std::string result;
while (a > 0)
{
T digit = a % base;
result = char((digit < 10 ? '0' : ('a' - 10)) + digit) + result;
a /= base;
}
if (negate)
result = "-" + result;
return result;
}
您可以使用 is_signed
funtcion, and whether it is unsigned using the is_unsigned
函数检查类型是否已签名。
要将类型转换为相应的签名版本,请使用 make_signed
and to the corresponding unsigned vesrion use make_unsigned
。
抱歉,直到现在才阅读 C++98 部分。
T 的符号可以推导为 std::is_signed<T>::value
从
http://en.cppreference.com/w/cpp/types/is_signed
也请查看整个 type support 库,了解有关类型静态属性的最终其他类似函数。
base
的类型应该是
std::conditional<std::is_signed<T>::value, int, unsigned>::type
Pre-C++11 你可以使用 std::conditional
:
的这个实现
template<bool B, class T, class F>
struct conditional { typedef T type; };
template<class T, class F>
struct conditional<false, T, F> { typedef F type; };
然后我们可以编写一个结构来提取类型的符号:
template <typename T>
struct signedness {
typedef typename conditional<T(-1)<T(0),int,unsigned>::type type;
};
然后只需将 base
声明为该类型即可:
std::string IntToString(T a,
typename signedness<T>::type base = 10){
下面的代码生成带有 -Wsign-conversion
的警告。它在 T digit = a % base
.
我想提取 T
的签名,然后将 base
转换为该签名以消除警告。
我试图避免专业化,因为那只会重复代码(唯一要改变的是 base
的签名)。我还试图避免将 base
强制转换为 T
,以防它是非 POD 类型,例如 Integer
(针对 longs
的缩减进行了优化)。
如何提取 T
的符号?
相关,代码库实际上是 C++98 和 C++03,因此它没有一些功能(如 Partial template specialization based on “signed-ness” of integer type? 中讨论的)。
template <class T>
std::string IntToString(T a, unsigned int base = 10)
{
if (a == 0)
return "0";
bool negate = false;
if (a < 0)
{
negate = true;
a = 0-a; // VC .NET does not like -a
}
std::string result;
while (a > 0)
{
T digit = a % base;
result = char((digit < 10 ? '0' : ('a' - 10)) + digit) + result;
a /= base;
}
if (negate)
result = "-" + result;
return result;
}
您可以使用 is_signed
funtcion, and whether it is unsigned using the is_unsigned
函数检查类型是否已签名。
要将类型转换为相应的签名版本,请使用 make_signed
and to the corresponding unsigned vesrion use make_unsigned
。
抱歉,直到现在才阅读 C++98 部分。
T 的符号可以推导为 std::is_signed<T>::value
从
http://en.cppreference.com/w/cpp/types/is_signed
也请查看整个 type support 库,了解有关类型静态属性的最终其他类似函数。
base
的类型应该是
std::conditional<std::is_signed<T>::value, int, unsigned>::type
Pre-C++11 你可以使用 std::conditional
:
template<bool B, class T, class F>
struct conditional { typedef T type; };
template<class T, class F>
struct conditional<false, T, F> { typedef F type; };
然后我们可以编写一个结构来提取类型的符号:
template <typename T>
struct signedness {
typedef typename conditional<T(-1)<T(0),int,unsigned>::type type;
};
然后只需将 base
声明为该类型即可:
std::string IntToString(T a,
typename signedness<T>::type base = 10){