aboutsummaryrefslogtreecommitdiff
path: root/libstdc++-v3/include
diff options
context:
space:
mode:
authorJonathan Wakely <jwakely@redhat.com>2016-10-03 18:01:10 +0100
committerJonathan Wakely <redi@gcc.gnu.org>2016-10-03 18:01:10 +0100
commit606dda21c8bcd4c2574e5b28f8125f01e38955c6 (patch)
treefbbf846d1547d0889eb640b9c224bef9cb11882b /libstdc++-v3/include
parentec9d5ad13bf6a965007d727d0dcbc77155e8132a (diff)
downloadgcc-606dda21c8bcd4c2574e5b28f8125f01e38955c6.zip
gcc-606dda21c8bcd4c2574e5b28f8125f01e38955c6.tar.gz
gcc-606dda21c8bcd4c2574e5b28f8125f01e38955c6.tar.bz2
Define std::gcd and std::lcm for C++17
* doc/xml/manual/status_cxx2017.xml: Update gcd/lcm status. * doc/html/*: Regenerate. * include/experimental/numeric (__abs): Move to <numeric>. (gcd, lcm): Use __detail::gcd and __detail::lcm. * include/std/numeric (__detail::__abs_integral) (__detail::__gcd, __detail::__lcm): Define. (gcd, lcm): Define for C++17. * testsuite/26_numerics/gcd/1.cc: New test. * testsuite/26_numerics/lcm/1.cc: New test. * testsuite/experimental/numeric/gcd.cc: Swap contents with ... * testsuite/experimental/numeric/lcd.cc: ... this. From-SVN: r240723
Diffstat (limited to 'libstdc++-v3/include')
-rw-r--r--libstdc++-v3/include/experimental/numeric28
-rw-r--r--libstdc++-v3/include/std/numeric79
2 files changed, 83 insertions, 24 deletions
diff --git a/libstdc++-v3/include/experimental/numeric b/libstdc++-v3/include/experimental/numeric
index 5089772..6d1dc21 100644
--- a/libstdc++-v3/include/experimental/numeric
+++ b/libstdc++-v3/include/experimental/numeric
@@ -52,44 +52,24 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
#define __cpp_lib_experimental_gcd_lcm 201411
- // std::abs is not constexpr and doesn't support unsigned integers.
- template<typename _Tp>
- constexpr
- enable_if_t<__and_<is_integral<_Tp>, is_signed<_Tp>>::value, _Tp>
- __abs(_Tp __val)
- { return __val < 0 ? -__val : __val; }
-
- template<typename _Tp>
- constexpr
- enable_if_t<__and_<is_integral<_Tp>, is_unsigned<_Tp>>::value, _Tp>
- __abs(_Tp __val)
- { return __val; }
-
- // Greatest common divisor
+ /// Greatest common divisor
template<typename _Mn, typename _Nn>
constexpr common_type_t<_Mn, _Nn>
gcd(_Mn __m, _Nn __n)
{
static_assert(is_integral<_Mn>::value, "arguments to gcd are integers");
static_assert(is_integral<_Nn>::value, "arguments to gcd are integers");
-
- return __m == 0 ? fundamentals_v2::__abs(__n)
- : __n == 0 ? fundamentals_v2::__abs(__m)
- : fundamentals_v2::gcd(__n, __m % __n);
+ return std::__detail::__gcd(__m, __n);
}
- // Least common multiple
+ /// Least common multiple
template<typename _Mn, typename _Nn>
constexpr common_type_t<_Mn, _Nn>
lcm(_Mn __m, _Nn __n)
{
static_assert(is_integral<_Mn>::value, "arguments to lcm are integers");
static_assert(is_integral<_Nn>::value, "arguments to lcm are integers");
-
- return (__m != 0 && __n != 0)
- ? (fundamentals_v2::__abs(__m) / fundamentals_v2::gcd(__m, __n))
- * fundamentals_v2::__abs(__n)
- : 0;
+ return std::__detail::__lcm(__m, __n);
}
_GLIBCXX_END_NAMESPACE_VERSION
diff --git a/libstdc++-v3/include/std/numeric b/libstdc++-v3/include/std/numeric
index 47a7cb8..7b1ab98 100644
--- a/libstdc++-v3/include/std/numeric
+++ b/libstdc++-v3/include/std/numeric
@@ -74,4 +74,83 @@
* math functions.
*/
+#if __cplusplus >= 201402L
+#include <type_traits>
+
+namespace std _GLIBCXX_VISIBILITY(default)
+{
+namespace __detail
+{
+_GLIBCXX_BEGIN_NAMESPACE_VERSION
+
+ // std::abs is not constexpr and doesn't support unsigned integers.
+ template<typename _Tp>
+ constexpr
+ enable_if_t<__and_<is_integral<_Tp>, is_signed<_Tp>>::value, _Tp>
+ __abs_integral(_Tp __val)
+ { return __val < 0 ? -__val : __val; }
+
+ template<typename _Tp>
+ constexpr
+ enable_if_t<__and_<is_integral<_Tp>, is_unsigned<_Tp>>::value, _Tp>
+ __abs_integral(_Tp __val)
+ { return __val; }
+
+ template<typename _Mn, typename _Nn>
+ constexpr common_type_t<_Mn, _Nn>
+ __gcd(_Mn __m, _Nn __n)
+ {
+ return __m == 0 ? __detail::__abs_integral(__n)
+ : __n == 0 ? __detail::__abs_integral(__m)
+ : __detail::__gcd(__n, __m % __n);
+ }
+
+ /// Least common multiple
+ template<typename _Mn, typename _Nn>
+ constexpr common_type_t<_Mn, _Nn>
+ __lcm(_Mn __m, _Nn __n)
+ {
+ return (__m != 0 && __n != 0)
+ ? (__detail::__abs_integral(__m) / __detail::__gcd(__m, __n))
+ * __detail::__abs_integral(__n)
+ : 0;
+ }
+
+_GLIBCXX_END_NAMESPACE_VERSION
+}
+
+_GLIBCXX_BEGIN_NAMESPACE_VERSION
+
+#if __cplusplus > 201402L
+
+#define __cpp_lib_gcd 201606
+ /// Greatest common divisor
+ template<typename _Mn, typename _Nn>
+ constexpr common_type_t<_Mn, _Nn>
+ gcd(_Mn __m, _Nn __n)
+ {
+ static_assert(is_integral<_Mn>::value, "arguments to gcd are integers");
+ static_assert(is_integral<_Nn>::value, "arguments to gcd are integers");
+ return __detail::__gcd(__m, __n);
+ }
+
+#define __cpp_lib_lcm 201606
+ /// Least common multiple
+ template<typename _Mn, typename _Nn>
+ constexpr common_type_t<_Mn, _Nn>
+ lcm(_Mn __m, _Nn __n)
+ {
+ static_assert(is_integral<_Mn>::value, "arguments to lcm are integers");
+ static_assert(is_integral<_Nn>::value, "arguments to lcm are integers");
+ return __detail::__lcm(__m, __n);
+ }
+
+#endif // C++17
+
+_GLIBCXX_END_NAMESPACE_VERSION
+} // namespace std
+
+#endif // C++14
+
+
#endif /* _GLIBCXX_NUMERIC */