Added thirdparty: boost library

This commit is contained in:
Viacheslav Demydiuk
2024-01-06 19:55:56 +02:00
parent bf49f439e1
commit bccd1e7051
15683 changed files with 3239840 additions and 0 deletions
+119
View File
@@ -0,0 +1,119 @@
// Boost.Geometry (aka GGL, Generic Geometry Library)
// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
// Copyright (c) 2008-2012 Bruno Lalande, Paris, France.
// Copyright (c) 2009-2012 Mateusz Loskot, London, UK.
// This file was modified by Oracle on 2020-2021.
// Modifications copyright (c) 2020-2021 Oracle and/or its affiliates.
// Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
// Parts of Boost.Geometry are redesigned from Geodan's Geographic Library
// (geolib/GGL), copyright (c) 1995-2010 Geodan, Amsterdam, the Netherlands.
// 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)
#ifndef BOOST_GEOMETRY_VIEWS_BOX_VIEW_HPP
#define BOOST_GEOMETRY_VIEWS_BOX_VIEW_HPP
#include <array>
#include <boost/geometry/algorithms/detail/assign_box_corners.hpp>
#include <boost/geometry/core/point_order.hpp>
#include <boost/geometry/core/point_type.hpp>
#include <boost/geometry/core/tag.hpp>
namespace boost { namespace geometry
{
// NOTE: This is equivalent to the previous implementation with detail::points_view.
// Technically this should not be called a view because it owns the elements.
// It's also not a borrowed_range because of dangling iterators after the
// destruction.
// It's a container or more specifically a ring of some sort, e.g. static_ring.
// NOTE: It would be possible to implement a borrowed_range or a view.
// The iterators would have to store copies of points.
// Another possibility is to store the original Box or reference/pointer
// to Box and index. But then the reference would be the value type
// so technically they would be InputIterators not RandomAccessIterators.
// NOTE: This object can not represent a Box correctly in all coordinates systems.
// It's correct only in cartesian CS so maybe it should be removed entirely.
/*!
\brief Makes a box behave like a ring or a range
\details Adapts a box to the Boost.Range concept, enabling the user to iterating
box corners. The box_view is registered as a Ring Concept
\tparam Box \tparam_geometry{Box}
\tparam Clockwise If true, walks in clockwise direction, otherwise
it walks in counterclockwise direction
\ingroup views
\qbk{before.synopsis,
[heading Model of]
[link geometry.reference.concepts.concept_ring Ring Concept]
}
\qbk{[include reference/views/box_view.qbk]}
*/
template <typename Box, bool Clockwise = true>
struct box_view
{
using array_t = std::array<typename geometry::point_type<Box>::type, 5>;
using iterator = typename array_t::const_iterator;
using const_iterator = typename array_t::const_iterator;
/// Constructor accepting the box to adapt
explicit box_view(Box const& box)
{
detail::assign_box_corners_oriented<!Clockwise>(box, m_array);
m_array[4] = m_array[0];
}
const_iterator begin() const noexcept { return m_array.begin(); }
const_iterator end() const noexcept { return m_array.end(); }
private:
array_t m_array;
};
#ifndef DOXYGEN_NO_TRAITS_SPECIALIZATIONS
// All views on boxes are handled as rings
namespace traits
{
template<typename Box, bool Clockwise>
struct tag<box_view<Box, Clockwise> >
{
typedef ring_tag type;
};
template<typename Box>
struct point_order<box_view<Box, false> >
{
static order_selector const value = counterclockwise;
};
template<typename Box>
struct point_order<box_view<Box, true> >
{
static order_selector const value = clockwise;
};
}
#endif // DOXYGEN_NO_TRAITS_SPECIALIZATIONS
}} // namespace boost::geometry
#endif // BOOST_GEOMETRY_VIEWS_BOX_VIEW_HPP
+151
View File
@@ -0,0 +1,151 @@
// Boost.Geometry (aka GGL, Generic Geometry Library)
// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
// Copyright (c) 2008-2012 Bruno Lalande, Paris, France.
// Copyright (c) 2009-2012 Mateusz Loskot, London, UK.
// This file was modified by Oracle on 2020-2023.
// Modifications copyright (c) 2020-2023 Oracle and/or its affiliates.
// Contributed and/or modified by Vissarion Fysikopoulos, on behalf of Oracle
// Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
// Parts of Boost.Geometry are redesigned from Geodan's Geographic Library
// (geolib/GGL), copyright (c) 1995-2010 Geodan, Amsterdam, the Netherlands.
// 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)
#ifndef BOOST_GEOMETRY_VIEWS_CLOSEABLE_VIEW_HPP
#define BOOST_GEOMETRY_VIEWS_CLOSEABLE_VIEW_HPP
#include <boost/geometry/core/closure.hpp>
#include <boost/geometry/core/point_order.hpp>
#include <boost/geometry/core/ring_type.hpp>
#include <boost/geometry/core/tag.hpp>
#include <boost/geometry/core/tags.hpp>
#include <boost/geometry/iterators/closing_iterator.hpp>
#include <boost/geometry/views/identity_view.hpp>
namespace boost { namespace geometry
{
#ifndef DOXYGEN_NO_DETAIL
namespace detail
{
template <typename Range>
struct closing_view
{
using iterator = closing_iterator<Range const>;
using const_iterator = closing_iterator<Range const>;
// Keep this explicit, important for nested views/ranges
explicit inline closing_view(Range const& r)
: m_begin(r)
, m_end(r, true)
{}
inline const_iterator begin() const { return m_begin; }
inline const_iterator end() const { return m_end; }
private:
const_iterator m_begin;
const_iterator m_end;
};
template
<
typename Range,
closure_selector Close = geometry::closure<Range>::value
>
struct closed_view
: identity_view<Range>
{
explicit inline closed_view(Range const& r)
: identity_view<Range const>(r)
{}
};
template <typename Range>
struct closed_view<Range, open>
: closing_view<Range>
{
explicit inline closed_view(Range const& r)
: closing_view<Range const>(r)
{}
};
} // namespace detail
#endif // DOXYGEN_NO_DETAIL
/*!
\brief View on a range, either closing it or leaving it as it is
\details The closeable_view is used internally by the library to handle all rings,
either closed or open, the same way. The default method is closed, all
algorithms process rings as if they are closed. Therefore, if they are opened,
a view is created which closes them.
The closeable_view might be used by library users, but its main purpose is
internally.
\tparam Range Original range
\tparam Close Specifies if it the range is closed, if so, nothing will happen.
If it is open, it will iterate the first point after the last point.
\ingroup views
*/
template <typename Range, closure_selector Close>
struct closeable_view {};
#ifndef DOXYGEN_NO_SPECIALIZATIONS
template <typename Range>
struct closeable_view<Range, closed>
{
using type = identity_view<Range>;
};
template <typename Range>
struct closeable_view<Range, open>
{
using type = detail::closing_view<Range>;
};
#endif // DOXYGEN_NO_SPECIALIZATIONS
#ifndef DOXYGEN_NO_TRAITS_SPECIALIZATIONS
namespace traits
{
template <typename Range, closure_selector Close>
struct tag<geometry::detail::closed_view<Range, Close> >
: geometry::tag<Range>
{};
template <typename Range, closure_selector Close>
struct point_order<geometry::detail::closed_view<Range, Close> >
: geometry::point_order<Range>
{};
template <typename Range, closure_selector Close>
struct closure<geometry::detail::closed_view<Range, Close> >
{
static const closure_selector value = closed;
};
} // namespace traits
#endif // DOXYGEN_NO_TRAITS_SPECIALIZATIONS
}} // namespace boost::geometry
#endif // BOOST_GEOMETRY_VIEWS_CLOSEABLE_VIEW_HPP
+16
View File
@@ -0,0 +1,16 @@
// Boost.Geometry (aka GGL, Generic Geometry Library)
// Copyright (c) 2015, Oracle and/or its affiliates.
// Contributed and/or modified by Menelaos Karavelas, on behalf of Oracle
// Licensed under the Boost Software License version 1.0.
// http://www.boost.org/users/license.html
#ifndef BOOST_GEOMETRY_VIEWS_DETAIL_BOUNDARY_VIEW_HPP
#define BOOST_GEOMETRY_VIEWS_DETAIL_BOUNDARY_VIEW_HPP
#include <boost/geometry/views/detail/boundary_view/interface.hpp>
#include <boost/geometry/views/detail/boundary_view/implementation.hpp>
#endif // BOOST_GEOMETRY_VIEWS_DETAIL_BOUNDARY_VIEW_HPP
@@ -0,0 +1,460 @@
// Boost.Geometry (aka GGL, Generic Geometry Library)
// Copyright (c) 2015-2020 Oracle and/or its affiliates.
// Contributed and/or modified by Menelaos Karavelas, on behalf of Oracle
// Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
// Licensed under the Boost Software License version 1.0.
// http://www.boost.org/users/license.html
#ifndef BOOST_GEOMETRY_VIEWS_DETAIL_BOUNDARY_VIEW_IMPLEMENTATION_HPP
#define BOOST_GEOMETRY_VIEWS_DETAIL_BOUNDARY_VIEW_IMPLEMENTATION_HPP
#include <cstddef>
#include <algorithm>
#include <iterator>
#include <memory>
#include <new>
#include <type_traits>
#include <utility>
#include <vector>
#include <boost/core/addressof.hpp>
#include <boost/iterator/iterator_facade.hpp>
#include <boost/iterator/iterator_categories.hpp>
#include <boost/range/size.hpp>
#include <boost/geometry/algorithms/num_interior_rings.hpp>
#include <boost/geometry/core/assert.hpp>
#include <boost/geometry/core/closure.hpp>
#include <boost/geometry/core/exterior_ring.hpp>
#include <boost/geometry/core/interior_rings.hpp>
#include <boost/geometry/core/ring_type.hpp>
#include <boost/geometry/core/static_assert.hpp>
#include <boost/geometry/core/tags.hpp>
#include <boost/geometry/iterators/flatten_iterator.hpp>
#include <boost/geometry/util/range.hpp>
#include <boost/geometry/views/closeable_view.hpp>
#include <boost/geometry/views/detail/boundary_view/interface.hpp>
namespace boost { namespace geometry
{
#ifndef DOXYGEN_NO_DETAIL
namespace detail { namespace boundary_views
{
template
<
typename Polygon,
typename Value = typename ring_type<Polygon>::type,
typename Reference = typename ring_return_type<Polygon>::type,
typename Difference = typename boost::range_difference
<
typename std::remove_reference
<
typename interior_return_type<Polygon>::type
>::type
>::type
>
class polygon_rings_iterator
: public boost::iterator_facade
<
polygon_rings_iterator<Polygon, Value, Reference, Difference>,
Value,
boost::random_access_traversal_tag,
Reference,
Difference
>
{
typedef typename boost::range_size
<
typename std::remove_reference
<
typename interior_return_type<Polygon>::type
>::type
>::type size_type;
public:
// default constructor
polygon_rings_iterator()
: m_polygon(NULL)
, m_index(0)
{}
// for begin
polygon_rings_iterator(Polygon& polygon)
: m_polygon(boost::addressof(polygon))
, m_index(0)
{}
// for end
polygon_rings_iterator(Polygon& polygon, bool)
: m_polygon(boost::addressof(polygon))
, m_index(static_cast<size_type>(num_rings(polygon)))
{}
template
<
typename OtherPolygon,
typename OtherValue,
typename OtherReference,
typename OtherDifference
>
polygon_rings_iterator(polygon_rings_iterator
<
OtherPolygon,
OtherValue,
OtherReference,
OtherDifference
> const& other)
: m_polygon(other.m_polygon)
, m_index(other.m_index)
{
static const bool is_convertible
= std::is_convertible<OtherPolygon, Polygon>::value;
BOOST_GEOMETRY_STATIC_ASSERT((is_convertible),
"OtherPolygon has to be convertible to Polygon.",
OtherPolygon, Polygon);
}
private:
friend class boost::iterator_core_access;
template
<
typename OtherPolygon,
typename OtherValue,
typename OtherReference,
typename OtherDifference
>
friend class polygon_rings_iterator;
static inline std::size_t num_rings(Polygon const& polygon)
{
return geometry::num_interior_rings(polygon) + 1;
}
inline Reference dereference() const
{
if (m_index == 0)
{
return exterior_ring(*m_polygon);
}
return range::at(interior_rings(*m_polygon), m_index - 1);
}
template
<
typename OtherPolygon,
typename OtherValue,
typename OtherReference,
typename OtherDifference
>
inline bool equal(polygon_rings_iterator
<
OtherPolygon,
OtherValue,
OtherReference,
OtherDifference
> const& other) const
{
BOOST_GEOMETRY_ASSERT(m_polygon == other.m_polygon);
return m_index == other.m_index;
}
inline void increment()
{
++m_index;
}
inline void decrement()
{
--m_index;
}
template
<
typename OtherPolygon,
typename OtherValue,
typename OtherReference,
typename OtherDifference
>
inline Difference distance_to(polygon_rings_iterator
<
OtherPolygon,
OtherValue,
OtherReference,
OtherDifference
> const& other) const
{
return static_cast<Difference>(other.m_index)
- static_cast<Difference>(m_index);
}
inline void advance(Difference n)
{
m_index += n;
}
private:
Polygon* m_polygon;
size_type m_index;
};
template <typename Ring>
class ring_boundary : closeable_view<Ring, closure<Ring>::value>::type
{
private:
typedef typename closeable_view<Ring, closure<Ring>::value>::type base_type;
public:
typedef typename base_type::iterator iterator;
typedef typename base_type::const_iterator const_iterator;
typedef linestring_tag tag_type;
explicit ring_boundary(Ring& ring)
: base_type(ring) {}
iterator begin() { return base_type::begin(); }
iterator end() { return base_type::end(); }
const_iterator begin() const { return base_type::begin(); }
const_iterator end() const { return base_type::end(); }
};
template <typename Geometry, typename Tag = typename tag<Geometry>::type>
struct num_rings
{};
template <typename Polygon>
struct num_rings<Polygon, polygon_tag>
{
static inline std::size_t apply(Polygon const& polygon)
{
return geometry::num_interior_rings(polygon) + 1;
}
};
template <typename MultiPolygon>
struct num_rings<MultiPolygon, multi_polygon_tag>
{
static inline std::size_t apply(MultiPolygon const& multipolygon)
{
return geometry::num_interior_rings(multipolygon)
+ static_cast<std::size_t>(boost::size(multipolygon));
}
};
template <typename Geometry, typename Tag = typename tag<Geometry>::type>
struct views_container_initializer
{};
template <typename Polygon>
struct views_container_initializer<Polygon, polygon_tag>
{
template <typename BoundaryView>
static inline void apply(Polygon const& polygon, BoundaryView* views)
{
typedef polygon_rings_iterator<Polygon> rings_iterator_type;
std::uninitialized_copy(rings_iterator_type(polygon),
rings_iterator_type(polygon, true),
views);
}
};
template <typename MultiPolygon>
class views_container_initializer<MultiPolygon, multi_polygon_tag>
{
typedef std::conditional_t
<
std::is_const<MultiPolygon>::value,
typename boost::range_value<MultiPolygon>::type const,
typename boost::range_value<MultiPolygon>::type
> polygon_type;
typedef polygon_rings_iterator<polygon_type> inner_iterator_type;
struct polygon_rings_begin
{
static inline inner_iterator_type apply(polygon_type& polygon)
{
return inner_iterator_type(polygon);
}
};
struct polygon_rings_end
{
static inline inner_iterator_type apply(polygon_type& polygon)
{
return inner_iterator_type(polygon, true);
}
};
typedef flatten_iterator
<
typename boost::range_iterator<MultiPolygon>::type,
inner_iterator_type,
typename std::iterator_traits<inner_iterator_type>::value_type,
polygon_rings_begin,
polygon_rings_end,
typename std::iterator_traits<inner_iterator_type>::reference
> rings_iterator_type;
public:
template <typename BoundaryView>
static inline void apply(MultiPolygon const& multipolygon,
BoundaryView* views)
{
rings_iterator_type first(boost::begin(multipolygon),
boost::end(multipolygon));
rings_iterator_type last(boost::end(multipolygon));
std::uninitialized_copy(first, last, views);
}
};
template <typename Areal>
class areal_boundary
{
typedef boundary_view<typename ring_type<Areal>::type> boundary_view_type;
typedef views_container_initializer<Areal> exception_safe_initializer;
template <typename T>
struct automatic_deallocator
{
automatic_deallocator(T* ptr) : m_ptr(ptr) {}
~automatic_deallocator()
{
operator delete(m_ptr);
}
inline void release() { m_ptr = NULL; }
T* m_ptr;
};
inline void initialize_views(Areal const& areal)
{
// initialize number of rings
std::size_t n_rings = num_rings<Areal>::apply(areal);
if (n_rings == 0)
{
return;
}
// allocate dynamic memory
boundary_view_type* views_ptr = static_cast
<
boundary_view_type*
>(operator new(sizeof(boundary_view_type) * n_rings));
// initialize; if exceptions are thrown by constructors
// they are handled automatically by automatic_deallocator
automatic_deallocator<boundary_view_type> deallocator(views_ptr);
exception_safe_initializer::apply(areal, views_ptr);
deallocator.release();
// now initialize member variables safely
m_views = views_ptr;
m_num_rings = n_rings;
}
// disallow copies and/or assignments
areal_boundary(areal_boundary const&);
areal_boundary& operator=(areal_boundary const&);
public:
typedef boundary_view_type* iterator;
typedef boundary_view_type const* const_iterator;
typedef multi_linestring_tag tag_type;
explicit areal_boundary(Areal& areal)
: m_views(NULL)
, m_num_rings(0)
{
initialize_views(areal);
}
~areal_boundary()
{
boundary_view_type* last = m_views + m_num_rings;
for (boundary_view_type* it = m_views; it != last; ++it)
{
it->~boundary_view_type();
}
operator delete(m_views);
}
inline iterator begin() { return m_views; }
inline iterator end() { return m_views + m_num_rings; }
inline const_iterator begin() const { return m_views; }
inline const_iterator end() const { return m_views + m_num_rings; }
private:
boundary_view_type* m_views;
std::size_t m_num_rings;
};
}} // namespace detail::boundary_view
#endif // DOXYGEN_NO_DETAIL
#ifndef DOXYGEN_NO_DISPATCH
namespace detail_dispatch
{
template <typename Ring>
struct boundary_view<Ring, ring_tag>
: detail::boundary_views::ring_boundary<Ring>
{
explicit boundary_view(Ring& ring)
: detail::boundary_views::ring_boundary<Ring>(ring)
{}
};
template <typename Polygon>
struct boundary_view<Polygon, polygon_tag>
: detail::boundary_views::areal_boundary<Polygon>
{
explicit boundary_view(Polygon& polygon)
: detail::boundary_views::areal_boundary<Polygon>(polygon)
{}
};
template <typename MultiPolygon>
struct boundary_view<MultiPolygon, multi_polygon_tag>
: detail::boundary_views::areal_boundary<MultiPolygon>
{
explicit boundary_view(MultiPolygon& multipolygon)
: detail::boundary_views::areal_boundary
<
MultiPolygon
>(multipolygon)
{}
};
} // namespace detail_dispatch
#endif // DOXYGEN_NO_DISPATCH
}} // namespace boost::geometry
#endif // BOOST_GEOMETRY_VIEWS_DETAIL_BOUNDARY_VIEW_IMPLEMENTATION_HPP
@@ -0,0 +1,70 @@
// Boost.Geometry (aka GGL, Generic Geometry Library)
// Copyright (c) 2015, Oracle and/or its affiliates.
// Contributed and/or modified by Menelaos Karavelas, on behalf of Oracle
// Licensed under the Boost Software License version 1.0.
// http://www.boost.org/users/license.html
#ifndef BOOST_GEOMETRY_VIEWS_DETAIL_BOUNDARY_VIEW_INTERFACE_HPP
#define BOOST_GEOMETRY_VIEWS_DETAIL_BOUNDARY_VIEW_INTERFACE_HPP
#include <boost/geometry/core/tag.hpp>
#include <boost/geometry/algorithms/not_implemented.hpp>
namespace boost { namespace geometry
{
#ifndef DOXYGEN_NO_DISPATCH
namespace detail_dispatch
{
template <typename Geometry, typename Tag = typename tag<Geometry>::type>
struct boundary_view
: not_implemented<Tag>
{};
} // namespace detail_dispatch
#endif // DOXYGEN_NO_DISPATCH
#ifndef DOXYGEN_NO_DETAIL
namespace detail
{
template <typename Geometry>
struct boundary_view
: detail_dispatch::boundary_view<Geometry>
{
explicit boundary_view(Geometry& geometry)
: detail_dispatch::boundary_view<Geometry>(geometry)
{}
};
} // namespace detail
#endif // DOXYGEN_NO_DETAIL
#ifndef DOXYGEN_NO_TRAITS_SPECIALIZATIONS
namespace traits
{
template <typename Geometry>
struct tag< geometry::detail::boundary_view<Geometry> >
{
typedef typename detail_dispatch::boundary_view
<
Geometry
>::tag_type type;
};
} // namespace traits
#endif // DOXYGEN_NO_TRAITS_SPECIALIZATIONS
}} // namespace boost::geometry
#endif // BOOST_GEOMETRY_VIEWS_DETAIL_BOUNDARY_VIEW_INTERFACE_HPP
@@ -0,0 +1,99 @@
// Boost.Geometry (aka GGL, Generic Geometry Library)
// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
// Copyright (c) 2008-2012 Bruno Lalande, Paris, France.
// Copyright (c) 2009-2012 Mateusz Loskot, London, UK.
// This file was modified by Oracle on 2014-2021.
// Modifications copyright (c) 2014-2023 Oracle and/or its affiliates.
// Contributed and/or modified by Vissarion Fysikopoulos, on behalf of Oracle
// Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
// Parts of Boost.Geometry are redesigned from Geodan's Geographic Library
// (geolib/GGL), copyright (c) 1995-2010 Geodan, Amsterdam, the Netherlands.
// 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)
#ifndef BOOST_GEOMETRY_VIEWS_DETAIL_CLOSED_CLOCKWISE_VIEW_HPP
#define BOOST_GEOMETRY_VIEWS_DETAIL_CLOSED_CLOCKWISE_VIEW_HPP
#include <type_traits>
#include <boost/range/begin.hpp>
#include <boost/range/end.hpp>
#include <boost/range/iterator.hpp>
#include <boost/geometry/views/closeable_view.hpp>
#include <boost/geometry/views/reversible_view.hpp>
#include <boost/geometry/util/order_as_direction.hpp>
#include <boost/geometry/util/type_traits_std.hpp>
namespace boost { namespace geometry
{
#ifndef DOXYGEN_NO_DETAIL
namespace detail
{
template
<
typename Range,
closure_selector Closure = geometry::closure<Range>::value,
order_selector Order = geometry::point_order<Range>::value
>
struct closed_clockwise_view
{
using closed_view = detail::closed_view<Range const, Closure>;
using view = detail::clockwise_view<closed_view const, Order>;
explicit inline closed_clockwise_view(Range const& r)
: m_view(closed_view(r))
{}
using iterator = typename boost::range_iterator<view const>::type;
using const_iterator = typename boost::range_iterator<view const>::type;
inline const_iterator begin() const { return boost::begin(m_view); }
inline const_iterator end() const { return boost::end(m_view); }
private:
view m_view;
};
} // namespace detail
#endif // DOXYGEN_NO_DETAIL
#ifndef DOXYGEN_NO_TRAITS_SPECIALIZATIONS
namespace traits
{
template <typename Range, closure_selector Closure, order_selector Order>
struct tag<geometry::detail::closed_clockwise_view<Range, Closure, Order> >
: geometry::tag<Range>
{};
template <typename Range, closure_selector Closure, order_selector Order>
struct point_order<geometry::detail::closed_clockwise_view<Range, Closure, Order> >
{
static const order_selector value = clockwise;
};
template <typename Range, closure_selector Closure, order_selector Order>
struct closure<geometry::detail::closed_clockwise_view<Range, Closure, Order> >
{
static const closure_selector value = closed;
};
} // namespace traits
#endif // DOXYGEN_NO_TRAITS_SPECIALIZATIONS
}} // namespace boost::geometry
#endif // BOOST_GEOMETRY_VIEWS_DETAIL_CLOSED_CLOCKWISE_VIEW_HPP
@@ -0,0 +1,84 @@
// Boost.Geometry
// Copyright (c) 2022, Oracle and/or its affiliates.
// Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
// Licensed under the Boost Software License version 1.0.
// http://www.boost.org/users/license.html
#ifndef BOOST_GEOMETRY_VIEWS_GEOMETRY_COLLECTION_VIEW_HPP
#define BOOST_GEOMETRY_VIEWS_GEOMETRY_COLLECTION_VIEW_HPP
#include <boost/core/addressof.hpp>
#include <boost/geometry/core/geometry_types.hpp>
#include <boost/geometry/core/tag.hpp>
#include <boost/geometry/core/tags.hpp>
#include <boost/geometry/core/visit.hpp>
#include <boost/geometry/util/sequence.hpp>
namespace boost { namespace geometry
{
namespace detail
{
template <typename Geometry>
class geometry_collection_view
{
public:
using iterator = Geometry const*;
using const_iterator = Geometry const*;
explicit geometry_collection_view(Geometry const& geometry)
: m_geometry(geometry)
{}
const_iterator begin() const { return boost::addressof(m_geometry); }
const_iterator end() const { return boost::addressof(m_geometry) + 1; }
private:
Geometry const& m_geometry;
};
} // namespace detail
#ifndef DOXYGEN_NO_TRAITS_SPECIALIZATIONS
namespace traits
{
template <typename Geometry>
struct tag<geometry::detail::geometry_collection_view<Geometry>>
{
using type = geometry_collection_tag;
};
template <typename Geometry>
struct geometry_types<geometry::detail::geometry_collection_view<Geometry>>
{
using type = util::type_sequence<Geometry>;
};
template <typename Geometry>
struct iter_visit<geometry::detail::geometry_collection_view<Geometry>>
{
template <typename Function, typename Iterator>
static void apply(Function && function, Iterator iterator)
{
function(*iterator);
}
};
} // namespace traits
#endif // DOXYGEN_NO_TRAITS_SPECIALIZATIONS
}} // namespace boost::geometry
#endif // BOOST_GEOMETRY_VIEWS_GEOMETRY_COLLECTION_VIEW_HPP
+123
View File
@@ -0,0 +1,123 @@
// Boost.Geometry (aka GGL, Generic Geometry Library)
// Copyright (c) 2007-2015 Barend Gehrels, Amsterdam, the Netherlands.
// Copyright (c) 2008-2015 Bruno Lalande, Paris, France.
// Copyright (c) 2009-2015 Mateusz Loskot, London, UK.
// Copyright (c) 2014-2015 Adam Wulkiewicz, Lodz, Poland
// This file was modified by Oracle on 2015.
// Modifications copyright (c) 2015, Oracle and/or its affiliates.
// Contributed and/or modified by Menelaos Karavelas, 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)
#ifndef BOOST_GEOMETRY_VIEWS_DETAIL_INDEXED_POINT_VIEW_HPP
#define BOOST_GEOMETRY_VIEWS_DETAIL_INDEXED_POINT_VIEW_HPP
#include <cstddef>
#include <boost/geometry/core/access.hpp>
#include <boost/geometry/core/coordinate_type.hpp>
#include <boost/geometry/core/coordinate_system.hpp>
#include <boost/geometry/core/coordinate_dimension.hpp>
#include <boost/geometry/util/math.hpp>
namespace boost { namespace geometry
{
namespace detail
{
template <typename Geometry, std::size_t Index>
class indexed_point_view
{
indexed_point_view & operator=(indexed_point_view const&);
public:
typedef typename geometry::point_type<Geometry>::type point_type;
typedef typename geometry::coordinate_type<Geometry>::type coordinate_type;
indexed_point_view(Geometry & geometry)
: m_geometry(geometry)
{}
template <std::size_t Dimension>
inline coordinate_type get() const
{
return geometry::get<Index, Dimension>(m_geometry);
}
template <std::size_t Dimension>
inline void set(coordinate_type const& value)
{
geometry::set<Index, Dimension>(m_geometry, value);
}
private:
Geometry & m_geometry;
};
}
#ifndef DOXYGEN_NO_TRAITS_SPECIALIZATIONS
namespace traits
{
template <typename Geometry, std::size_t Index>
struct tag< geometry::detail::indexed_point_view<Geometry, Index> >
{
typedef point_tag type;
};
template <typename Geometry, std::size_t Index>
struct coordinate_type< geometry::detail::indexed_point_view<Geometry, Index> >
{
typedef typename geometry::coordinate_type<Geometry>::type type;
};
template <typename Geometry, std::size_t Index>
struct coordinate_system
<
geometry::detail::indexed_point_view<Geometry, Index>
>
{
typedef typename geometry::coordinate_system<Geometry>::type type;
};
template <typename Geometry, std::size_t Index>
struct dimension< geometry::detail::indexed_point_view<Geometry, Index> >
: geometry::dimension<Geometry>
{};
template<typename Geometry, std::size_t Index, std::size_t Dimension>
struct access
<
geometry::detail::indexed_point_view<Geometry, Index>, Dimension
>
{
typedef typename geometry::coordinate_type<Geometry>::type coordinate_type;
static inline coordinate_type get(
geometry::detail::indexed_point_view<Geometry, Index> const& p)
{
return p.template get<Dimension>();
}
static inline void set(
geometry::detail::indexed_point_view<Geometry, Index> & p,
coordinate_type const& value)
{
p.template set<Dimension>(value);
}
};
} // namespace traits
#endif // DOXYGEN_NO_TRAITS_SPECIALIZATIONS
}} // namespace boost::geometry
#endif // BOOST_GEOMETRY_VIEWS_DETAIL_INDEXED_POINT_VIEW_HPP
+222
View File
@@ -0,0 +1,222 @@
// Boost.Geometry
// Copyright (c) 2022-2023, Oracle and/or its affiliates.
// Contributed and/or modified by Vissarion Fysikopoulos, on behalf of Oracle
// Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
// Licensed under the Boost Software License version 1.0.
// http://www.boost.org/users/license.html
#ifndef BOOST_GEOMETRY_VIEWS_DETAIL_RANDOM_ACCESS_VIEW_HPP
#define BOOST_GEOMETRY_VIEWS_DETAIL_RANDOM_ACCESS_VIEW_HPP
#include <vector>
#include <boost/range/begin.hpp>
#include <boost/range/end.hpp>
#include <boost/range/iterator.hpp>
#include <boost/range/size.hpp>
#include <boost/geometry/algorithms/detail/visit.hpp>
#include <boost/geometry/core/geometry_types.hpp>
#include <boost/geometry/core/tag.hpp>
#include <boost/geometry/core/tags.hpp>
#include <boost/geometry/util/sequence.hpp>
#include <boost/geometry/util/type_traits.hpp>
namespace boost { namespace geometry
{
#ifndef DOXYGEN_NO_DETAIL
namespace detail
{
template <typename Range>
struct is_random_access_range
: std::is_convertible
<
typename boost::iterator_traversal
<
typename boost::range_iterator<Range>::type
>::type,
boost::random_access_traversal_tag
>
{};
template <typename Geometry>
struct is_geometry_collection_recursive
: util::bool_constant
<
util::is_geometry_collection
<
typename util::sequence_find_if
<
typename traits::geometry_types<std::remove_const_t<Geometry>>::type,
util::is_geometry_collection
>::type
>::value
>
{};
template
<
typename GeometryCollection,
bool IsRandomAccess = is_random_access_range<GeometryCollection>::value,
bool IsRecursive = is_geometry_collection_recursive<GeometryCollection>::value
>
class random_access_view
: public std::vector<typename boost::range_iterator<GeometryCollection>::type>
{
// NOTE: An alternative would be to implement iterator holding base iterators
// to geometry collections of lower levels to process after the current level
// of bfs traversal is finished.
using base_t = std::vector<typename boost::range_iterator<GeometryCollection>::type>;
public:
random_access_view(GeometryCollection & geometry)
{
this->reserve(boost::size(geometry));
detail::visit_breadth_first_impl<true>::apply([&](auto&&, auto iter)
{
this->push_back(iter);
return true;
}, geometry);
}
};
template <typename GeometryCollection>
class random_access_view<GeometryCollection, true, false>
{
public:
using iterator = typename boost::range_iterator<GeometryCollection>::type;
using const_iterator = typename boost::range_const_iterator<GeometryCollection>::type;
random_access_view(GeometryCollection & geometry)
: m_begin(boost::begin(geometry))
, m_end(boost::end(geometry))
{}
iterator begin() { return m_begin; }
iterator end() { return m_end; }
const_iterator begin() const { return m_begin; }
const_iterator end() const { return m_end; }
private:
iterator m_begin, m_end;
};
template <typename GeometryCollection>
struct random_access_view_iter_visit
{
template <typename Function, typename Iterator>
static void apply(Function && function, Iterator iterator)
{
geometry::traits::iter_visit
<
std::remove_const_t<GeometryCollection>
>::apply(std::forward<Function>(function), *iterator);
}
};
template <typename ...Ts>
struct remove_geometry_collections_pack
{
using type = util::type_sequence<>;
};
template <typename T, typename ...Ts>
struct remove_geometry_collections_pack<T, Ts...>
{
using next_sequence = typename remove_geometry_collections_pack<Ts...>::type;
using type = std::conditional_t
<
util::is_geometry_collection<T>::value,
next_sequence,
typename util::sequence_merge<util::type_sequence<T>, next_sequence>::type
>;
};
template <typename Types>
struct remove_geometry_collections;
template <typename ...Ts>
struct remove_geometry_collections<util::type_sequence<Ts...>>
: remove_geometry_collections_pack<Ts...>
{};
} // namespace detail
#endif // DOXYGEN_NO_DETAIL
#ifndef DOXYGEN_NO_TRAITS_SPECIALIZATIONS
namespace traits
{
template<typename GeometryCollection, bool IsRandomAccess, bool IsRecursive>
struct tag<geometry::detail::random_access_view<GeometryCollection, IsRandomAccess, IsRecursive>>
{
using type = geometry_collection_tag;
};
template <typename GeometryCollection>
struct iter_visit<geometry::detail::random_access_view<GeometryCollection, false, false>>
: geometry::detail::random_access_view_iter_visit<GeometryCollection>
{};
template <typename GeometryCollection>
struct iter_visit<geometry::detail::random_access_view<GeometryCollection, true, true>>
: geometry::detail::random_access_view_iter_visit<GeometryCollection>
{};
template <typename GeometryCollection>
struct iter_visit<geometry::detail::random_access_view<GeometryCollection, false, true>>
: geometry::detail::random_access_view_iter_visit<GeometryCollection>
{};
template <typename GeometryCollection>
struct iter_visit<geometry::detail::random_access_view<GeometryCollection, true, false>>
{
template <typename Function, typename Iterator>
static void apply(Function && function, Iterator iterator)
{
geometry::traits::iter_visit
<
std::remove_const_t<GeometryCollection>
>::apply(std::forward<Function>(function), iterator);
}
};
template <typename GeometryCollection, bool IsRandomAccess>
struct geometry_types<geometry::detail::random_access_view<GeometryCollection, IsRandomAccess, false>>
: traits::geometry_types
<
std::remove_const_t<GeometryCollection>
>
{};
template <typename GeometryCollection, bool IsRandomAccess>
struct geometry_types<geometry::detail::random_access_view<GeometryCollection, IsRandomAccess, true>>
: geometry::detail::remove_geometry_collections
<
typename traits::geometry_types
<
std::remove_const_t<GeometryCollection>
>::type
>
{};
} // namespace traits
#endif // DOXYGEN_NO_TRAITS_SPECIALIZATIONS
}} // namespace boost::geometry
#endif // BOOST_GEOMETRY_VIEWS_DETAIL_RANDOM_ACCESS_VIEW_HPP
+195
View File
@@ -0,0 +1,195 @@
// Boost.Geometry (aka GGL, Generic Geometry Library)
// Copyright (c) 2015-2020, Oracle and/or its affiliates.
// Contributed and/or modified by Menelaos Karavelas, on behalf of Oracle
// Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
// Licensed under the Boost Software License version 1.0.
// http://www.boost.org/users/license.html
#ifndef BOOST_GEOMETRY_VIEWS_DETAIL_TWO_DIMENSIONAL_VIEW_HPP
#define BOOST_GEOMETRY_VIEWS_DETAIL_TWO_DIMENSIONAL_VIEW_HPP
#include <cstddef>
#include <boost/geometry/core/access.hpp>
#include <boost/geometry/core/coordinate_type.hpp>
#include <boost/geometry/core/coordinate_system.hpp>
#include <boost/geometry/core/coordinate_dimension.hpp>
#include <boost/geometry/core/point_type.hpp>
#include <boost/geometry/core/static_assert.hpp>
#include <boost/geometry/core/tag.hpp>
#include <boost/geometry/core/tags.hpp>
#include <boost/geometry/algorithms/not_implemented.hpp>
namespace boost { namespace geometry
{
#ifndef DOXYGEN_NO_DETAIL
namespace detail
{
template
<
typename Geometry,
std::size_t Dimension1 = 0,
std::size_t Dimension2 = 1,
typename Tag = typename tag<Geometry>::type
>
struct two_dimensional_view
: not_implemented<Tag>
{};
// View that enables to choose two dimensions of a point and see it as
// a two-dimensional point
template <typename Point, std::size_t Dimension1, std::size_t Dimension2>
struct two_dimensional_view<Point, Dimension1, Dimension2, point_tag>
{
BOOST_GEOMETRY_STATIC_ASSERT(
(Dimension1 < dimension<Point>::value),
"Coordinate Dimension1 is larger than Point's dimension.",
std::integral_constant<std::size_t, Dimension1>);
BOOST_GEOMETRY_STATIC_ASSERT(
(Dimension2 < dimension<Point>::value),
"Coordinate Dimension2 is larger than Point's dimension.",
std::integral_constant<std::size_t, Dimension2>);
two_dimensional_view(Point& point)
: m_point(point)
{}
Point& m_point;
};
} // namespace detail
#endif // DOXYGEN_NO_DETAIL
#ifndef DOXYGEN_NO_TRAITS_SPECIALIZATIONS
namespace traits
{
template <typename Point, std::size_t Dimension1, std::size_t Dimension2>
struct tag
<
geometry::detail::two_dimensional_view
<
Point, Dimension1, Dimension2, point_tag
>
>
{
typedef point_tag type;
};
template <typename Point, std::size_t Dimension1, std::size_t Dimension2>
struct coordinate_system
<
geometry::detail::two_dimensional_view
<
Point, Dimension1, Dimension2, point_tag
>
> : coordinate_system<typename geometry::point_type<Point>::type>
{};
template <typename Point, std::size_t Dimension1, std::size_t Dimension2>
struct coordinate_type
<
geometry::detail::two_dimensional_view
<
Point, Dimension1, Dimension2, point_tag
>
> : coordinate_type<typename geometry::point_type<Point>::type>
{};
template <typename Point, std::size_t Dimension1, std::size_t Dimension2>
struct dimension
<
geometry::detail::two_dimensional_view
<
Point, Dimension1, Dimension2, point_tag
>
> : std::integral_constant<std::size_t, 2>
{};
template <typename Point, std::size_t Dimension1, std::size_t Dimension2>
struct point_type
<
geometry::detail::two_dimensional_view
<
Point, Dimension1, Dimension2, point_tag
>
>
{
typedef typename geometry::point_type<Point>::type type;
};
template <typename Point, std::size_t Dimension1, std::size_t Dimension2>
struct access
<
geometry::detail::two_dimensional_view
<
Point, Dimension1, Dimension2, point_tag
>,
0
>
{
typedef typename geometry::coordinate_type<Point>::type coordinate_type;
typedef geometry::detail::two_dimensional_view
<
Point, Dimension1, Dimension2, point_tag
> view_type;
static inline coordinate_type get(view_type const& view)
{
return geometry::get<Dimension1>(view.m_point);
}
static inline void set(view_type& view, coordinate_type const& value)
{
geometry::set<Dimension1>(view.m_point, value);
}
};
template <typename Point, std::size_t Dimension1, std::size_t Dimension2>
struct access
<
geometry::detail::two_dimensional_view
<
Point, Dimension1, Dimension2, point_tag
>,
1
>
{
typedef typename geometry::coordinate_type<Point>::type coordinate_type;
typedef geometry::detail::two_dimensional_view
<
Point, Dimension1, Dimension2, point_tag
> view_type;
static inline coordinate_type get(view_type const& view)
{
return geometry::get<Dimension2>(view.m_point);
}
static inline void set(view_type& view, coordinate_type const& value)
{
geometry::set<Dimension2>(view.m_point, value);
}
};
} // namespace traits
#endif // DOXYGEN_NO_TRAITS_SPECIALIZATIONS
}} // namespace boost::geometry
#endif // BOOST_GEOMETRY_VIEWS_DETAIL_TWO_DIMENSIONAL_VIEW_HPP
+70
View File
@@ -0,0 +1,70 @@
// Boost.Geometry (aka GGL, Generic Geometry Library)
// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
// Copyright (c) 2008-2012 Bruno Lalande, Paris, France.
// Copyright (c) 2009-2012 Mateusz Loskot, London, UK.
// This file was modified by Oracle on 2020-2021.
// Modifications copyright (c) 2020-2021 Oracle and/or its affiliates.
// Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
// Parts of Boost.Geometry are redesigned from Geodan's Geographic Library
// (geolib/GGL), copyright (c) 1995-2010 Geodan, Amsterdam, the Netherlands.
// 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)
#ifndef BOOST_GEOMETRY_VIEWS_IDENTITY_VIEW_HPP
#define BOOST_GEOMETRY_VIEWS_IDENTITY_VIEW_HPP
#include <boost/range/iterator_range.hpp>
#include <boost/range/begin.hpp>
#include <boost/range/end.hpp>
namespace boost { namespace geometry
{
// Silence warning C4512: assignment operator could not be generated
#if defined(_MSC_VER)
#pragma warning(push)
#pragma warning(disable : 4512)
#endif
/*!
\brief View on a range, not modifying anything
\tparam Range original range
\ingroup views
*/
template <typename Range>
struct identity_view
{
using const_iterator = typename boost::range_iterator<Range const>::type;
using iterator = typename boost::range_iterator<Range>::type;
explicit inline identity_view(Range& r)
: m_begin(boost::begin(r))
, m_end(boost::end(r))
{}
inline const_iterator begin() const { return m_begin; }
inline const_iterator end() const { return m_end; }
inline iterator begin() { return m_begin; }
inline iterator end() { return m_end; }
private:
iterator m_begin;
iterator m_end;
};
#if defined(_MSC_VER)
#pragma warning(pop)
#endif
}} // namespace boost::geometry
#endif // BOOST_GEOMETRY_VIEWS_IDENTITY_VIEW_HPP
+129
View File
@@ -0,0 +1,129 @@
// Boost.Geometry (aka GGL, Generic Geometry Library)
// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
// Copyright (c) 2008-2012 Bruno Lalande, Paris, France.
// Copyright (c) 2009-2012 Mateusz Loskot, London, UK.
// This file was modified by Oracle on 2020-2023.
// Modifications copyright (c) 2020-2023 Oracle and/or its affiliates.
// Contributed and/or modified by Vissarion Fysikopoulos, on behalf of Oracle
// Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
// Parts of Boost.Geometry are redesigned from Geodan's Geographic Library
// (geolib/GGL), copyright (c) 1995-2010 Geodan, Amsterdam, the Netherlands.
// 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)
#ifndef BOOST_GEOMETRY_VIEWS_REVERSIBLE_VIEW_HPP
#define BOOST_GEOMETRY_VIEWS_REVERSIBLE_VIEW_HPP
#include <boost/version.hpp>
#include <boost/range/adaptor/reversed.hpp>
#include <boost/geometry/core/closure.hpp>
#include <boost/geometry/core/point_order.hpp>
#include <boost/geometry/core/ring_type.hpp>
#include <boost/geometry/core/tag.hpp>
#include <boost/geometry/core/tags.hpp>
#include <boost/geometry/util/order_as_direction.hpp>
#include <boost/geometry/views/identity_view.hpp>
namespace boost { namespace geometry
{
#ifndef DOXYGEN_NO_DETAIL
namespace detail
{
template
<
typename Range,
order_selector Order = geometry::point_order<Range>::value
>
struct clockwise_view
: identity_view<Range>
{
explicit inline clockwise_view(Range& r)
: identity_view<Range>(r)
{}
};
template <typename Range>
struct clockwise_view<Range, counterclockwise>
: boost::reversed_range<Range>
{
explicit inline clockwise_view(Range& r)
: boost::reversed_range<Range>(r)
{}
};
} // namespace detail
#endif // DOXYGEN_NO_DETAIL
/*!
\brief View on a range, reversing direction if necessary
\tparam Range original range
\tparam Direction direction of iteration
\ingroup views
*/
template <typename Range, iterate_direction Direction>
struct reversible_view {};
#ifndef DOXYGEN_NO_SPECIALIZATIONS
template <typename Range>
struct reversible_view<Range, iterate_forward>
{
using type = identity_view<Range>;
};
template <typename Range>
struct reversible_view<Range, iterate_reverse>
{
using type = boost::reversed_range<Range>;
};
#endif // DOXYGEN_NO_SPECIALIZATIONS
#ifndef DOXYGEN_NO_TRAITS_SPECIALIZATIONS
namespace traits
{
template <typename Range, order_selector Order>
struct tag<geometry::detail::clockwise_view<Range, Order> >
: geometry::tag<Range>
{};
template <typename Range, order_selector Order>
struct point_order<geometry::detail::clockwise_view<Range, Order> >
{
static const order_selector value = clockwise;
};
template <typename Range, order_selector Order>
struct closure<geometry::detail::clockwise_view<Range, Order> >
: geometry::closure<Range>
{};
} // namespace traits
#endif // DOXYGEN_NO_TRAITS_SPECIALIZATIONS
}} // namespace boost::geometry
#endif // BOOST_GEOMETRY_VIEWS_REVERSIBLE_VIEW_HPP
+102
View File
@@ -0,0 +1,102 @@
// Boost.Geometry (aka GGL, Generic Geometry Library)
// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
// Copyright (c) 2008-2012 Bruno Lalande, Paris, France.
// Copyright (c) 2009-2012 Mateusz Loskot, London, UK.
// This file was modified by Oracle on 2020-2021.
// Modifications copyright (c) 2020-2021 Oracle and/or its affiliates.
// Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
// Parts of Boost.Geometry are redesigned from Geodan's Geographic Library
// (geolib/GGL), copyright (c) 1995-2010 Geodan, Amsterdam, the Netherlands.
// 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)
#ifndef BOOST_GEOMETRY_VIEWS_SEGMENT_VIEW_HPP
#define BOOST_GEOMETRY_VIEWS_SEGMENT_VIEW_HPP
#include <array>
#include <boost/geometry/algorithms/detail/assign_indexed_point.hpp>
#include <boost/geometry/core/point_type.hpp>
#include <boost/geometry/core/tag.hpp>
namespace boost { namespace geometry
{
// NOTE: This is equivalent to the previous implementation with detail::points_view.
// Technically this should not be called a view because it owns the elements.
// It's also not a borrowed_range because of dangling iterators after the
// destruction.
// It's a container or more specifically a linestring of some sort, e.g. static_linestring.
// NOTE: It would be possible to implement a borrowed_range or a view.
// The iterators would have to store copies of points.
// Another possibility is to store the original Segment or reference/pointer
// to Segment and index. But then the reference would be the value type
// so technically they would be InputIterators not RandomAccessIterators.
/*!
\brief Makes a segment behave like a linestring or a range
\details Adapts a segment to the Boost.Range concept, enabling the user to
iterate the two segment points. The segment_view is registered as a LineString Concept
\tparam Segment \tparam_geometry{Segment}
\ingroup views
\qbk{before.synopsis,
[heading Model of]
[link geometry.reference.concepts.concept_linestring LineString Concept]
}
\qbk{[include reference/views/segment_view.qbk]}
*/
template <typename Segment>
struct segment_view
{
using array_t = std::array<typename geometry::point_type<Segment>::type, 2>;
using iterator = typename array_t::const_iterator;
using const_iterator = typename array_t::const_iterator;
/// Constructor accepting the segment to adapt
explicit segment_view(Segment const& segment)
{
geometry::detail::assign_point_from_index<0>(segment, m_array[0]);
geometry::detail::assign_point_from_index<1>(segment, m_array[1]);
}
const_iterator begin() const noexcept { return m_array.begin(); }
const_iterator end() const noexcept { return m_array.end(); }
private:
array_t m_array;
};
#ifndef DOXYGEN_NO_TRAITS_SPECIALIZATIONS
// All segment ranges can be handled as linestrings
namespace traits
{
template<typename Segment>
struct tag<segment_view<Segment> >
{
typedef linestring_tag type;
};
}
#endif // DOXYGEN_NO_TRAITS_SPECIALIZATIONS
}} // namespace boost::geometry
#endif // BOOST_GEOMETRY_VIEWS_SEGMENT_VIEW_HPP