Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-01-18 09:35:03

0001 // Boost.Geometry (aka GGL, Generic Geometry Library)
0002 
0003 // Copyright (c) 2007-2014 Barend Gehrels, Amsterdam, the Netherlands.
0004 // Copyright (c) 2008-2014 Bruno Lalande, Paris, France.
0005 // Copyright (c) 2009-2014 Mateusz Loskot, London, UK.
0006 // Copyright (c) 2013-2014 Adam Wulkiewicz, Lodz, Poland.
0007 
0008 // This file was modified by Oracle on 2013-2022.
0009 // Modifications copyright (c) 2013-2022, Oracle and/or its affiliates.
0010 
0011 // Contributed and/or modified by Vissarion Fysikopoulos, on behalf of Oracle
0012 // Contributed and/or modified by Menelaos Karavelas, on behalf of Oracle
0013 // Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
0014 
0015 // Parts of Boost.Geometry are redesigned from Geodan's Geographic Library
0016 // (geolib/GGL), copyright (c) 1995-2010 Geodan, Amsterdam, the Netherlands.
0017 
0018 // Use, modification and distribution is subject to the Boost Software License,
0019 // Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
0020 // http://www.boost.org/LICENSE_1_0.txt)
0021 
0022 #ifndef BOOST_GEOMETRY_ALGORITHMS_DETAIL_DISJOINT_LINEAR_AREAL_HPP
0023 #define BOOST_GEOMETRY_ALGORITHMS_DETAIL_DISJOINT_LINEAR_AREAL_HPP
0024 
0025 #include <iterator>
0026 
0027 #include <boost/range/begin.hpp>
0028 #include <boost/range/end.hpp>
0029 #include <boost/range/value_type.hpp>
0030 
0031 #include <boost/geometry/core/closure.hpp>
0032 #include <boost/geometry/core/point_type.hpp>
0033 #include <boost/geometry/core/ring_type.hpp>
0034 #include <boost/geometry/core/exterior_ring.hpp>
0035 #include <boost/geometry/core/interior_rings.hpp>
0036 #include <boost/geometry/core/tag.hpp>
0037 #include <boost/geometry/core/tag_cast.hpp>
0038 #include <boost/geometry/core/tags.hpp>
0039 
0040 #include <boost/geometry/algorithms/detail/covered_by/implementation.hpp>
0041 #include <boost/geometry/algorithms/not_implemented.hpp>
0042 
0043 #include <boost/geometry/algorithms/detail/assign_indexed_point.hpp>
0044 #include <boost/geometry/algorithms/detail/point_on_border.hpp>
0045 
0046 #include <boost/geometry/algorithms/detail/disjoint/linear_linear.hpp>
0047 #include <boost/geometry/algorithms/detail/disjoint/linear_segment_or_box.hpp>
0048 #include <boost/geometry/algorithms/detail/disjoint/multirange_geometry.hpp>
0049 #include <boost/geometry/algorithms/detail/disjoint/point_box.hpp>
0050 #include <boost/geometry/algorithms/detail/disjoint/segment_box.hpp>
0051 
0052 #include <boost/geometry/algorithms/dispatch/disjoint.hpp>
0053 
0054 #include <boost/geometry/geometries/helper_geometry.hpp>
0055 
0056 namespace boost { namespace geometry
0057 {
0058 
0059 #ifndef DOXYGEN_NO_DETAIL
0060 namespace detail { namespace disjoint
0061 {
0062 
0063 template <typename Geometry1, typename Geometry2,
0064           typename Tag1 = typename tag<Geometry1>::type,
0065           typename Tag1OrMulti = typename tag_cast<Tag1, multi_tag>::type>
0066 struct disjoint_no_intersections_policy
0067 {
0068     /*!
0069     \tparam Strategy point_in_geometry strategy
0070     */
0071     template <typename Strategy>
0072     static inline bool apply(Geometry1 const& g1, Geometry2 const& g2, Strategy const& strategy)
0073     {
0074         using point_type = typename point_type<Geometry1>::type;
0075         typename helper_geometry<point_type>::type p;
0076         geometry::point_on_border(p, g1);
0077 
0078         return ! geometry::covered_by(p, g2, strategy);
0079     }
0080 };
0081 
0082 template <typename Geometry1, typename Geometry2, typename Tag1>
0083 struct disjoint_no_intersections_policy<Geometry1, Geometry2, Tag1, multi_tag>
0084 {
0085     /*!
0086     \tparam Strategy point_in_geometry strategy
0087     */
0088     template <typename Strategy>
0089     static inline bool apply(Geometry1 const& g1, Geometry2 const& g2, Strategy const& strategy)
0090     {
0091         // TODO: use partition or rtree on g2
0092         for (auto it = boost::begin(g1); it != boost::end(g1); ++it)
0093         {
0094             typedef typename boost::range_value<Geometry1 const>::type value_type;
0095             if (! disjoint_no_intersections_policy<value_type const, Geometry2>
0096                     ::apply(*it, g2, strategy))
0097             {
0098                 return false;
0099             }
0100         }
0101         return true;
0102     }
0103 };
0104 
0105 
0106 template<typename Geometry1, typename Geometry2,
0107          typename NoIntersectionsPolicy
0108                     = disjoint_no_intersections_policy<Geometry1, Geometry2> >
0109 struct disjoint_linear_areal
0110 {
0111     /*!
0112     \tparam Strategy relate (segments intersection) strategy
0113     */
0114     template <typename Strategy>
0115     static inline bool apply(Geometry1 const& g1, Geometry2 const& g2, Strategy const& strategy)
0116     {
0117         // if there are intersections - return false
0118         if ( !disjoint_linear<Geometry1, Geometry2>::apply(g1, g2, strategy) )
0119         {
0120             return false;
0121         }
0122 
0123         return NoIntersectionsPolicy::apply(g1, g2, strategy);
0124     }
0125 };
0126 
0127 
0128 
0129 
0130 template
0131 <
0132     typename Segment,
0133     typename Areal,
0134     typename Tag = typename tag<Areal>::type
0135 >
0136 struct disjoint_segment_areal
0137     : not_implemented<Segment, Areal>
0138 {};
0139 
0140 
0141 template <typename Segment, typename Polygon>
0142 class disjoint_segment_areal<Segment, Polygon, polygon_tag>
0143 {
0144 
0145     template <typename InteriorRings, typename Strategy>
0146     static inline
0147     bool check_interior_rings(InteriorRings const& interior_rings,
0148                               Segment const& segment,
0149                               Strategy const& strategy)
0150     {
0151         using ring_type = typename boost::range_value<InteriorRings>::type;
0152 
0153         using unary_predicate_type = unary_disjoint_geometry_to_query_geometry
0154             <
0155                 Segment,
0156                 Strategy,
0157                 disjoint_range_segment_or_box<ring_type, Segment>
0158             >;
0159 
0160         return std::all_of(boost::begin(interior_rings),
0161                            boost::end(interior_rings),
0162                            unary_predicate_type(segment, strategy));
0163     }
0164 
0165 
0166 public:
0167     template <typename IntersectionStrategy>
0168     static inline bool apply(Segment const& segment,
0169                              Polygon const& polygon,
0170                              IntersectionStrategy const& strategy)
0171     {
0172         if (! disjoint_range_segment_or_box
0173                 <
0174                     typename geometry::ring_type<Polygon>::type,
0175                     Segment
0176                 >::apply(geometry::exterior_ring(polygon), segment, strategy))
0177         {
0178             return false;
0179         }
0180 
0181         if (! check_interior_rings(geometry::interior_rings(polygon), segment, strategy))
0182         {
0183             return false;
0184         }
0185 
0186         typename point_type<Segment>::type p;
0187         detail::assign_point_from_index<0>(segment, p);
0188 
0189         return ! geometry::covered_by(p, polygon, strategy);
0190     }
0191 };
0192 
0193 
0194 template <typename Segment, typename MultiPolygon>
0195 struct disjoint_segment_areal<Segment, MultiPolygon, multi_polygon_tag>
0196 {
0197     template <typename IntersectionStrategy>
0198     static inline bool apply(Segment const& segment, MultiPolygon const& multipolygon,
0199                              IntersectionStrategy const& strategy)
0200     {
0201         return multirange_constant_size_geometry
0202             <
0203                 MultiPolygon, Segment
0204             >::apply(multipolygon, segment, strategy);
0205     }
0206 };
0207 
0208 
0209 template <typename Segment, typename Ring>
0210 struct disjoint_segment_areal<Segment, Ring, ring_tag>
0211 {
0212     template <typename IntersectionStrategy>
0213     static inline bool apply(Segment const& segment,
0214                              Ring const& ring,
0215                              IntersectionStrategy const& strategy)
0216     {
0217         if (! disjoint_range_segment_or_box<Ring, Segment>::apply(ring, segment, strategy))
0218         {
0219             return false;
0220         }
0221 
0222         typename point_type<Segment>::type p;
0223         detail::assign_point_from_index<0>(segment, p);
0224 
0225         return ! geometry::covered_by(p, ring, strategy);
0226     }
0227 };
0228 
0229 
0230 }} // namespace detail::disjoint
0231 #endif // DOXYGEN_NO_DETAIL
0232 
0233 
0234 
0235 
0236 #ifndef DOXYGEN_NO_DISPATCH
0237 namespace dispatch
0238 {
0239 
0240 
0241 template <typename Linear, typename Areal>
0242 struct disjoint<Linear, Areal, 2, linear_tag, areal_tag, false>
0243     : public detail::disjoint::disjoint_linear_areal<Linear, Areal>
0244 {};
0245 
0246 
0247 template <typename Areal, typename Linear>
0248 struct disjoint<Areal, Linear, 2, areal_tag, linear_tag, false>
0249 {
0250     template <typename Strategy>
0251     static inline bool apply(Areal const& areal, Linear const& linear,
0252                              Strategy const& strategy)
0253     {
0254         return detail::disjoint::disjoint_linear_areal
0255             <
0256                 Linear, Areal
0257             >::apply(linear, areal, strategy);
0258     }
0259 };
0260 
0261 
0262 template <typename Areal, typename Segment>
0263 struct disjoint<Areal, Segment, 2, areal_tag, segment_tag, false>
0264 {
0265     template <typename Strategy>
0266     static inline bool apply(Areal const& g1, Segment const& g2,
0267                              Strategy const& strategy)
0268     {
0269         return detail::disjoint::disjoint_segment_areal
0270             <
0271                 Segment, Areal
0272             >::apply(g2, g1, strategy);
0273     }
0274 };
0275 
0276 
0277 template <typename Segment, typename Areal>
0278 struct disjoint<Segment, Areal, 2, segment_tag, areal_tag, false>
0279     : detail::disjoint::disjoint_segment_areal<Segment, Areal>
0280 {};
0281 
0282 
0283 } // namespace dispatch
0284 #endif // DOXYGEN_NO_DISPATCH
0285 
0286 
0287 }} // namespace boost::geometry
0288 
0289 
0290 #endif // BOOST_GEOMETRY_ALGORITHMS_DETAIL_DISJOINT_LINEAR_AREAL_HPP