]> git.proxmox.com Git - ceph.git/blobdiff - ceph/src/boost/boost/geometry/util/range.hpp
update ceph source to reef 18.1.2
[ceph.git] / ceph / src / boost / boost / geometry / util / range.hpp
index 1abf617aa3c9af9fa84738db4a7370a97b8fbd12..445636dd0f884d6879145118defca9c06cadccb5 100644 (file)
@@ -1,15 +1,13 @@
-// Boost.Geometry (aka GGL, Generic Geometry Library)
+// Boost.Geometry
 
 // Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
 
-// This file was modified by Oracle on 2013-2020.
-// Modifications copyright (c) 2013-2020 Oracle and/or its affiliates.
-
+// This file was modified by Oracle on 2013-2021.
+// Modifications copyright (c) 2013-2021 Oracle and/or its affiliates.
 // Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
 
-// Use, modification and distribution is subject to the Boost Software License,
-// Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
-// http://www.boost.org/LICENSE_1_0.txt)
+// Licensed under the Boost Software License version 1.0.
+// http://www.boost.org/users/license.html
 
 #ifndef BOOST_GEOMETRY_UTIL_RANGE_HPP
 #define BOOST_GEOMETRY_UTIL_RANGE_HPP
@@ -29,7 +27,6 @@
 #include <boost/range/difference_type.hpp>
 #include <boost/range/has_range_iterator.hpp>
 #include <boost/range/iterator.hpp>
-#include <boost/range/rbegin.hpp>
 #include <boost/range/reference.hpp>
 #include <boost/range/size.hpp>
 #include <boost/range/value_type.hpp>
@@ -75,37 +72,16 @@ struct is_range
     : is_range_impl<T>
 {};
 
+template <typename Range, typename T = void>
+using enable_if_mutable_t = std::enable_if_t
+    <
+        (! std::is_const<std::remove_reference_t<Range>>::value),
+        T
+    >;
 
-// NOTE: For SinglePassRanges pos could iterate over all elements until the i-th element was met.
-
-template <typename RandomAccessRange>
-struct pos
-{
-    typedef typename boost::range_iterator<RandomAccessRange>::type iterator;
-    typedef typename boost::range_size<RandomAccessRange>::type size_type;
-    typedef typename boost::range_difference<RandomAccessRange>::type difference_type;
-
-    static inline iterator apply(RandomAccessRange & rng, size_type i)
-    {
-        BOOST_RANGE_CONCEPT_ASSERT(( boost::RandomAccessRangeConcept<RandomAccessRange> ));
-        return boost::begin(rng) + static_cast<difference_type>(i);
-    }
-};
 
 } // namespace detail
 
-/*!
-\brief Short utility to conveniently return an iterator of a RandomAccessRange.
-\ingroup utility
-*/
-template <typename RandomAccessRange>
-inline typename boost::range_iterator<RandomAccessRange const>::type
-pos(RandomAccessRange const& rng,
-    typename boost::range_size<RandomAccessRange const>::type i)
-{
-    BOOST_GEOMETRY_ASSERT(i <= boost::size(rng));
-    return detail::pos<RandomAccessRange const>::apply(rng, i);
-}
 
 /*!
 \brief Short utility to conveniently return an iterator of a RandomAccessRange.
@@ -113,24 +89,13 @@ pos(RandomAccessRange const& rng,
 */
 template <typename RandomAccessRange>
 inline typename boost::range_iterator<RandomAccessRange>::type
-pos(RandomAccessRange & rng,
+pos(RandomAccessRange && rng,
     typename boost::range_size<RandomAccessRange>::type i)
 {
+    BOOST_RANGE_CONCEPT_ASSERT((boost::RandomAccessRangeConcept<RandomAccessRange>));
     BOOST_GEOMETRY_ASSERT(i <= boost::size(rng));
-    return detail::pos<RandomAccessRange>::apply(rng, i);
-}
-
-/*!
-\brief Short utility to conveniently return an element of a RandomAccessRange.
-\ingroup utility
-*/
-template <typename RandomAccessRange>
-inline typename boost::range_reference<RandomAccessRange const>::type
-at(RandomAccessRange const& rng,
-   typename boost::range_size<RandomAccessRange const>::type i)
-{
-    BOOST_GEOMETRY_ASSERT(i < boost::size(rng));
-    return * detail::pos<RandomAccessRange const>::apply(rng, i);
+    return boost::begin(rng)
+         + static_cast<typename boost::range_difference<RandomAccessRange>::type>(i);
 }
 
 /*!
@@ -139,11 +104,10 @@ at(RandomAccessRange const& rng,
 */
 template <typename RandomAccessRange>
 inline typename boost::range_reference<RandomAccessRange>::type
-at(RandomAccessRange & rng,
+at(RandomAccessRange && rng,
    typename boost::range_size<RandomAccessRange>::type i)
 {
-    BOOST_GEOMETRY_ASSERT(i < boost::size(rng));
-    return * detail::pos<RandomAccessRange>::apply(rng, i);
+    return *pos(rng, i);
 }
 
 /*!
@@ -151,76 +115,101 @@ at(RandomAccessRange & rng,
 \ingroup utility
 */
 template <typename Range>
-inline typename boost::range_reference<Range const>::type
-front(Range const& rng)
+inline typename boost::range_reference<Range>::type
+front(Range && rng)
 {
     BOOST_GEOMETRY_ASSERT(!boost::empty(rng));
     return *boost::begin(rng);
 }
 
 /*!
-\brief Short utility to conveniently return the front element of a Range.
+\brief Short utility to conveniently return the back element of a BidirectionalRange.
 \ingroup utility
 */
-template <typename Range>
-inline typename boost::range_reference<Range>::type
-front(Range & rng)
+template <typename BidirectionalRange>
+inline typename boost::range_reference<BidirectionalRange>::type
+back(BidirectionalRange && rng)
 {
+    BOOST_RANGE_CONCEPT_ASSERT((boost::BidirectionalRangeConcept<BidirectionalRange>));
     BOOST_GEOMETRY_ASSERT(!boost::empty(rng));
-    return *boost::begin(rng);
+    auto it = boost::end(rng);
+    return *(--it);
 }
 
-// NOTE: For SinglePassRanges back() could iterate over all elements until the last element is met.
 
 /*!
-\brief Short utility to conveniently return the back element of a BidirectionalRange.
+\brief Short utility to conveniently clear a mutable range.
+       It uses traits::clear<>.
 \ingroup utility
 */
-template <typename BidirectionalRange>
-inline typename boost::range_reference<BidirectionalRange const>::type
-back(BidirectionalRange const& rng)
+template
+<
+    typename Range,
+    detail::enable_if_mutable_t<Range, int> = 0
+>
+inline void clear(Range && rng)
 {
-    BOOST_RANGE_CONCEPT_ASSERT(( boost::BidirectionalRangeConcept<BidirectionalRange const> ));
-    BOOST_GEOMETRY_ASSERT(!boost::empty(rng));
-    return *(boost::rbegin(rng));
+    geometry::traits::clear
+        <
+            std::remove_reference_t<Range>
+        >::apply(rng);
 }
 
 /*!
-\brief Short utility to conveniently return the back element of a BidirectionalRange.
+\brief Short utility to conveniently insert a new element at the end of a mutable range.
+       It uses boost::geometry::traits::push_back<>.
 \ingroup utility
 */
-template <typename BidirectionalRange>
-inline typename boost::range_reference<BidirectionalRange>::type
-back(BidirectionalRange & rng)
+template
+<
+    typename Range,
+    detail::enable_if_mutable_t<Range, int> = 0
+>
+inline void push_back(Range && rng,
+                      typename boost::range_value<Range>::type const& value)
 {
-    BOOST_RANGE_CONCEPT_ASSERT((boost::BidirectionalRangeConcept<BidirectionalRange>));
-    BOOST_GEOMETRY_ASSERT(!boost::empty(rng));
-    return *(boost::rbegin(rng));
+    geometry::traits::push_back
+        <
+            std::remove_reference_t<Range>
+        >::apply(rng, value);
 }
 
-
 /*!
-\brief Short utility to conveniently clear a mutable range.
-       It uses traits::clear<>.
+\brief Short utility to conveniently insert a new element at the end of a mutable range.
+       It uses boost::geometry::traits::push_back<>.
 \ingroup utility
 */
-template <typename Range>
-inline void clear(Range & rng)
+template
+<
+    typename Range,
+    detail::enable_if_mutable_t<Range, int> = 0
+>
+inline void push_back(Range && rng,
+                      typename boost::range_value<Range>::type && value)
 {
-    // NOTE: this trait is probably not needed since it could be implemented using resize()
-    geometry::traits::clear<Range>::apply(rng);
+    geometry::traits::push_back
+        <
+            std::remove_reference_t<Range>
+        >::apply(rng, std::move(value));
 }
 
 /*!
 \brief Short utility to conveniently insert a new element at the end of a mutable range.
-       It uses boost::geometry::traits::push_back<>.
+       It uses boost::geometry::traits::emplace_back<>.
 \ingroup utility
 */
-template <typename Range>
-inline void push_back(Range & rng,
-                      typename boost::range_value<Range>::type const& value)
+template
+<
+    typename Range,
+    typename ...Args,
+    detail::enable_if_mutable_t<Range, int> = 0
+>
+inline void emplace_back(Range && rng, Args &&... args)
 {
-    geometry::traits::push_back<Range>::apply(rng, value);
+    geometry::traits::emplace_back
+        <
+            std::remove_reference_t<Range>
+        >::apply(rng, std::forward<Args>(args)...);
 }
 
 /*!
@@ -228,80 +217,48 @@ inline void push_back(Range & rng,
        It uses boost::geometry::traits::resize<>.
 \ingroup utility
 */
-template <typename Range>
-inline void resize(Range & rng,
+template
+<
+    typename Range,
+    detail::enable_if_mutable_t<Range, int> = 0
+>
+inline void resize(Range && rng,
                    typename boost::range_size<Range>::type new_size)
 {
-    geometry::traits::resize<Range>::apply(rng, new_size);
+    geometry::traits::resize
+        <
+            std::remove_reference_t<Range>
+        >::apply(rng, new_size);
 }
 
-
 /*!
 \brief Short utility to conveniently remove an element from the back of a mutable range.
        It uses resize().
 \ingroup utility
 */
-template <typename Range>
-inline void pop_back(Range & rng)
+template
+<
+    typename Range,
+    detail::enable_if_mutable_t<Range, int> = 0
+>
+inline void pop_back(Range && rng)
 {
     BOOST_GEOMETRY_ASSERT(!boost::empty(rng));
     range::resize(rng, boost::size(rng) - 1);
 }
 
-namespace detail {
-
-#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
-
-template <typename It,
-          typename OutIt,
-          bool UseMove = std::is_convertible
-                            <
-                                typename std::iterator_traits<It>::value_type &&,
-                                typename std::iterator_traits<OutIt>::value_type
-                            >::value>
-struct copy_or_move_impl
-{
-    static inline OutIt apply(It first, It last, OutIt out)
-    {
-        return std::move(first, last, out);
-    }
-};
-
-template <typename It, typename OutIt>
-struct copy_or_move_impl<It, OutIt, false>
-{
-    static inline OutIt apply(It first, It last, OutIt out)
-    {
-        return std::copy(first, last, out);
-    }
-};
-
-template <typename It, typename OutIt>
-inline OutIt copy_or_move(It first, It last, OutIt out)
-{
-    return copy_or_move_impl<It, OutIt>::apply(first, last, out);
-}
-
-#else
-
-template <typename It, typename OutIt>
-inline OutIt copy_or_move(It first, It last, OutIt out)
-{
-    return std::copy(first, last, out);
-}
-
-#endif
-
-} // namespace detail
-
 /*!
 \brief Short utility to conveniently remove an element from a mutable range.
-       It uses std::copy() and resize(). Version taking mutable iterators.
+       It uses std::move() and resize(). Version taking mutable iterators.
 \ingroup utility
 */
-template <typename Range>
+template
+<
+    typename Range,
+    detail::enable_if_mutable_t<Range, int> = 0
+>
 inline typename boost::range_iterator<Range>::type
-erase(Range & rng,
+erase(Range && rng,
       typename boost::range_iterator<Range>::type it)
 {
     BOOST_GEOMETRY_ASSERT(!boost::empty(rng));
@@ -314,7 +271,7 @@ erase(Range & rng,
         next = it;
     ++next;
 
-    detail::copy_or_move(next, boost::end(rng), it);
+    std::move(next, boost::end(rng), it);
     range::resize(rng, boost::size(rng) - 1);
 
     // NOTE: In general this should be sufficient:
@@ -328,13 +285,17 @@ erase(Range & rng,
 
 /*!
 \brief Short utility to conveniently remove an element from a mutable range.
-       It uses std::copy() and resize(). Version taking non-mutable iterators.
+       It uses std::move() and resize(). Version taking non-mutable iterators.
 \ingroup utility
 */
-template <typename Range>
+template
+<
+    typename Range,
+    detail::enable_if_mutable_t<Range, int> = 0
+>
 inline typename boost::range_iterator<Range>::type
-erase(Range & rng,
-      typename boost::range_iterator<Range const>::type cit)
+erase(Range && rng,
+      typename boost::range_iterator<std::remove_reference_t<Range> const>::type cit)
 {
     BOOST_RANGE_CONCEPT_ASSERT(( boost::RandomAccessRangeConcept<Range> ));
 
@@ -347,12 +308,16 @@ erase(Range & rng,
 
 /*!
 \brief Short utility to conveniently remove a range of elements from a mutable range.
-       It uses std::copy() and resize(). Version taking mutable iterators.
+       It uses std::move() and resize(). Version taking mutable iterators.
 \ingroup utility
 */
-template <typename Range>
+template
+<
+    typename Range,
+    detail::enable_if_mutable_t<Range, int> = 0
+>
 inline typename boost::range_iterator<Range>::type
-erase(Range & rng,
+erase(Range && rng,
       typename boost::range_iterator<Range>::type first,
       typename boost::range_iterator<Range>::type last)
 {
@@ -368,7 +333,7 @@ erase(Range & rng,
         typename boost::range_difference<Range>::type const
             d = std::distance(boost::begin(rng), first);
 
-        detail::copy_or_move(last, boost::end(rng), first);
+        std::move(last, boost::end(rng), first);
         range::resize(rng, boost::size(rng) - count);
 
         // NOTE: In general this should be sufficient:
@@ -385,14 +350,18 @@ erase(Range & rng,
 
 /*!
 \brief Short utility to conveniently remove a range of elements from a mutable range.
-       It uses std::copy() and resize(). Version taking non-mutable iterators.
+       It uses std::move() and resize(). Version taking non-mutable iterators.
 \ingroup utility
 */
-template <typename Range>
+template
+<
+    typename Range,
+    detail::enable_if_mutable_t<Range, int> = 0
+>
 inline typename boost::range_iterator<Range>::type
-erase(Range & rng,
-      typename boost::range_iterator<Range const>::type cfirst,
-      typename boost::range_iterator<Range const>::type clast)
+erase(Range && rng,
+      typename boost::range_iterator<std::remove_reference_t<Range> const>::type cfirst,
+      typename boost::range_iterator<std::remove_reference_t<Range> const>::type clast)
 {
     BOOST_RANGE_CONCEPT_ASSERT(( boost::RandomAccessRangeConcept<Range> ));
 
@@ -430,6 +399,12 @@ public:
         return *this;
     }
 
+    back_insert_iterator & operator=(typename Container::value_type && value)
+    {
+        range::push_back(*container, std::move(value));
+        return *this;
+    }
+
     back_insert_iterator & operator* ()
     {
         return *this;