std::numeric_limits<T>::is_modulo
From cppreference.com
static const bool is_modulo; |
(C++11まで) | |
| static constexpr bool is_modulo; |
(C++11以降) | |
std::numeric_limits<T>::is_modulo の値は、加算、減算、乗算、または除算の結果が範囲 [min(), max()] を超える場合に、その型のオーバーフローをモジュロ算術で処理するすべての算術型 T に対して true になります。つまり、このような演算によって返される値は、期待される値とは max() - min() + 1 の倍数だけ異なります。
実装が符号付き整数オーバーフローをラップすると定義していない限り、is_modulo は符号付き整数型に対して false になります。
目次 |
[編集] 標準特殊化
T
|
std::numeric_limits<T>::is_modulo の値 |
| /* 非特殊化 */ | false |
| bool | false |
| char | 実装定義 |
| signed char | 実装定義 |
| unsigned char | true |
| wchar_t | 実装定義 |
| char8_t (C++20 以降) | true |
| char16_t (C++11 以降) | true |
| char32_t (C++11 以降) | true |
| short | 実装定義 |
| unsigned short | true |
| int | 実装定義 |
| unsigned int | true |
| long | 実装定義 |
| unsigned long | true |
| long long (C++11) | 実装定義 |
| unsigned long long (C++11) | true |
| float | false |
| double | false |
| long double | false |
[編集] 備考
標準は、LWG issue 2422 の解決前は「ほとんどの機械では、これは符号付き整数に対して true である」と述べていました。GCC PR 22200 で関連する議論を参照してください。
[編集] 例
モジュロ型の動作を示します
このコードを実行
#include <iostream> #include <type_traits> #include <limits> template<class T> typename std::enable_if<std::numeric_limits<T>::is_modulo>::type check_overflow() { std::cout << "max value is " << std::numeric_limits<T>::max() << '\n' << "min value is " << std::numeric_limits<T>::min() << '\n' << "max value + 1 is " << std::numeric_limits<T>::max()+1 << '\n'; } int main() { check_overflow<int>(); std::cout << '\n'; check_overflow<unsigned long>(); // check_overflow<float>(); // compile-time error, not a modulo type }
実行結果の例
max value is 2147483647 min value is -2147483648 max value + 1 is -2147483648 max value is 18446744073709551615 min value is 0 max value + 1 is 0
[編集] 欠陥レポート
以下の動作変更を伴う欠陥報告が、以前に公開されたC++標準に遡って適用されました。
| DR | 適用対象 | 公開された動作 | 正しい動作 |
|---|---|---|---|
| LWG 612 | C++98 | 「モジュロ算術で オーバーフローを処理する」という定義は不十分だった[1] |
より良い 定義を提供した |
| LWG 2422 | C++98 | is_modulo はほとんどの機械で符号付き整数型に対して true である必要があった |
符号付き整数オーバーフローがラップすると定義されていない限り、 符号付き整数型に対して false である必要がある |
- ↑ 定義は「2つの正の数を加算すると、3番目のより小さい数にラップアラウンドする結果になる可能性がある」というものです。これには次の問題があります。
- ラップされた値が定義されていない。
- 結果が再現可能であるかどうかが述べられていない。
- 加算、減算、その他の操作をすべての値に対して実行すると、定義された動作になることが要求されていない。
[編集] 関連項目
| [static] |
整数型を識別する (public static member constant) |
| [static] |
IEC 559/IEEE 754 浮動小数点数型を識別する (public static member constant) |
| [static] |
厳密な型を識別する (public static member constant) |