1 // Boost.Geometry Index
3 // Spatial query predicates
5 // Copyright (c) 2011-2018 Adam Wulkiewicz, Lodz, Poland.
7 // This file was modified by Oracle on 2019-2020.
8 // Modifications copyright (c) 2019-2020 Oracle and/or its affiliates.
9 // Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
11 // Use, modification and distribution is subject to the Boost Software License,
12 // Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
13 // http://www.boost.org/LICENSE_1_0.txt)
15 #ifndef BOOST_GEOMETRY_INDEX_PREDICATES_HPP
16 #define BOOST_GEOMETRY_INDEX_PREDICATES_HPP
18 #include <boost/geometry/index/detail/predicates.hpp>
19 #include <boost/geometry/util/tuples.hpp>
22 \defgroup predicates Predicates (boost::geometry::index::)
25 namespace boost { namespace geometry { namespace index {
28 \brief Generate \c contains() predicate.
30 Generate a predicate defining Value and Geometry relationship. With this
31 predicate query returns indexed Values that contain passed Geometry.
32 Value is returned by the query if <tt>bg::within(Geometry, Indexable)</tt>
33 returns <tt>true</tt>.
37 bgi::query(spatial_index, bgi::contains(box), std::back_inserter(result));
42 \tparam Geometry The Geometry type.
44 \param g The Geometry object.
46 template <typename Geometry> inline
47 detail::predicates::spatial_predicate<Geometry, detail::predicates::contains_tag, false>
48 contains(Geometry const& g)
50 return detail::predicates::spatial_predicate
53 detail::predicates::contains_tag,
59 \brief Generate \c covered_by() predicate.
61 Generate a predicate defining Value and Geometry relationship. With this
62 predicate query returns indexed Values that are covered by passed Geometry.
63 Value is returned by the query if <tt>bg::covered_by(Indexable, Geometry)</tt>
64 returns <tt>true</tt>.
68 bgi::query(spatial_index, bgi::covered_by(box), std::back_inserter(result));
73 \tparam Geometry The Geometry type.
75 \param g The Geometry object.
77 template <typename Geometry> inline
78 detail::predicates::spatial_predicate<Geometry, detail::predicates::covered_by_tag, false>
79 covered_by(Geometry const& g)
81 return detail::predicates::spatial_predicate
84 detail::predicates::covered_by_tag,
90 \brief Generate \c covers() predicate.
92 Generate a predicate defining Value and Geometry relationship. With this
93 predicate query returns indexed Values that cover passed Geometry.
94 Value is returned by the query if <tt>bg::covered_by(Geometry, Indexable)</tt>
95 returns <tt>true</tt>.
99 bgi::query(spatial_index, bgi::covers(box), std::back_inserter(result));
104 \tparam Geometry The Geometry type.
106 \param g The Geometry object.
108 template <typename Geometry> inline
109 detail::predicates::spatial_predicate<Geometry, detail::predicates::covers_tag, false>
110 covers(Geometry const& g)
112 return detail::predicates::spatial_predicate
115 detail::predicates::covers_tag,
121 \brief Generate \c disjoint() predicate.
123 Generate a predicate defining Value and Geometry relationship. With this
124 predicate query returns indexed Values that are disjoint with passed Geometry.
125 Value is returned by the query if <tt>bg::disjoint(Indexable, Geometry)</tt>
126 returns <tt>true</tt>.
130 bgi::query(spatial_index, bgi::disjoint(box), std::back_inserter(result));
135 \tparam Geometry The Geometry type.
137 \param g The Geometry object.
139 template <typename Geometry> inline
140 detail::predicates::spatial_predicate<Geometry, detail::predicates::disjoint_tag, false>
141 disjoint(Geometry const& g)
143 return detail::predicates::spatial_predicate
146 detail::predicates::disjoint_tag,
152 \brief Generate \c intersects() predicate.
154 Generate a predicate defining Value and Geometry relationship. With this
155 predicate query returns indexed Values that intersect passed Geometry.
156 Value is returned by the query if <tt>bg::intersects(Indexable, Geometry)</tt>
157 returns <tt>true</tt>.
161 bgi::query(spatial_index, bgi::intersects(box), std::back_inserter(result));
162 bgi::query(spatial_index, bgi::intersects(ring), std::back_inserter(result));
163 bgi::query(spatial_index, bgi::intersects(polygon), std::back_inserter(result));
168 \tparam Geometry The Geometry type.
170 \param g The Geometry object.
172 template <typename Geometry> inline
173 detail::predicates::spatial_predicate<Geometry, detail::predicates::intersects_tag, false>
174 intersects(Geometry const& g)
176 return detail::predicates::spatial_predicate
179 detail::predicates::intersects_tag,
185 \brief Generate \c overlaps() predicate.
187 Generate a predicate defining Value and Geometry relationship. With this
188 predicate query returns indexed Values that overlap passed Geometry.
189 Value is returned by the query if <tt>bg::overlaps(Indexable, Geometry)</tt>
190 returns <tt>true</tt>.
194 bgi::query(spatial_index, bgi::overlaps(box), std::back_inserter(result));
199 \tparam Geometry The Geometry type.
201 \param g The Geometry object.
203 template <typename Geometry> inline
204 detail::predicates::spatial_predicate<Geometry, detail::predicates::overlaps_tag, false>
205 overlaps(Geometry const& g)
207 return detail::predicates::spatial_predicate
210 detail::predicates::overlaps_tag,
215 #ifdef BOOST_GEOMETRY_INDEX_DETAIL_EXPERIMENTAL
218 \brief Generate \c touches() predicate.
220 Generate a predicate defining Value and Geometry relationship. With this
221 predicate query returns indexed Values that touch passed Geometry.
222 Value is returned by the query if <tt>bg::touches(Indexable, Geometry)</tt>
223 returns <tt>true</tt>.
227 \tparam Geometry The Geometry type.
229 \param g The Geometry object.
231 template <typename Geometry> inline
232 detail::predicates::spatial_predicate<Geometry, detail::predicates::touches_tag, false>
233 touches(Geometry const& g)
235 return detail::predicates::spatial_predicate
238 detail::predicates::touches_tag,
243 #endif // BOOST_GEOMETRY_INDEX_DETAIL_EXPERIMENTAL
246 \brief Generate \c within() predicate.
248 Generate a predicate defining Value and Geometry relationship. With this
249 predicate query returns indexed Values that are within passed Geometry.
250 Value is returned by the query if <tt>bg::within(Indexable, Geometry)</tt>
251 returns <tt>true</tt>.
255 bgi::query(spatial_index, bgi::within(box), std::back_inserter(result));
260 \tparam Geometry The Geometry type.
262 \param g The Geometry object.
264 template <typename Geometry> inline
265 detail::predicates::spatial_predicate<Geometry, detail::predicates::within_tag, false>
266 within(Geometry const& g)
268 return detail::predicates::spatial_predicate
271 detail::predicates::within_tag,
277 \brief Generate satisfies() predicate.
279 A wrapper around user-defined UnaryPredicate checking if Value should be returned by spatial query.
283 bool is_red(Value const& v) { return v.is_red(); }
286 template <typename Value> bool operator()(Value const& v) { return v.is_red(); }
291 rt.query(index::intersects(box) && index::satisfies(is_red),
292 std::back_inserter(result));
294 rt.query(index::intersects(box) && index::satisfies(is_red_o()),
295 std::back_inserter(result));
297 #ifndef BOOST_NO_CXX11_LAMBDAS
298 rt.query(index::intersects(box) && index::satisfies([](Value const& v) { return v.is_red(); }),
299 std::back_inserter(result));
305 \tparam UnaryPredicate A type of unary predicate function or function object.
307 \param pred The unary predicate function or function object.
309 template <typename UnaryPredicate> inline
310 detail::predicates::satisfies<UnaryPredicate, false>
311 satisfies(UnaryPredicate const& pred)
313 return detail::predicates::satisfies<UnaryPredicate, false>(pred);
317 \brief Generate nearest() predicate.
319 When nearest predicate is passed to the query, k-nearest neighbour search will be performed.
320 \c nearest() predicate takes a \c Geometry from which distances to \c Values are calculated
321 and the maximum number of \c Values that should be returned. Internally
322 boost::geometry::comparable_distance() is used to perform the calculation.
326 bgi::query(spatial_index, bgi::nearest(pt, 5), std::back_inserter(result));
327 bgi::query(spatial_index, bgi::nearest(pt, 5) && bgi::intersects(box), std::back_inserter(result));
328 bgi::query(spatial_index, bgi::nearest(box, 5), std::back_inserter(result));
332 Only one \c nearest() predicate may be used in a query.
336 \param geometry The geometry from which distance is calculated.
337 \param k The maximum number of values to return.
339 template <typename Geometry> inline
340 detail::predicates::nearest<Geometry>
341 nearest(Geometry const& geometry, unsigned k)
343 return detail::predicates::nearest<Geometry>(geometry, k);
346 #ifdef BOOST_GEOMETRY_INDEX_DETAIL_EXPERIMENTAL
349 \brief Generate path() predicate.
351 When path predicate is passed to the query, the returned values are k values along the path closest to
352 its begin. \c path() predicate takes a \c Segment or a \c Linestring defining the path and the maximum
353 number of \c Values that should be returned.
357 bgi::query(spatial_index, bgi::path(segment, 5), std::back_inserter(result));
358 bgi::query(spatial_index, bgi::path(linestring, 5) && bgi::intersects(box), std::back_inserter(result));
362 Only one distance predicate (\c nearest() or \c path()) may be used in a query.
366 \param linestring The path along which distance is calculated.
367 \param k The maximum number of values to return.
369 template <typename SegmentOrLinestring> inline
370 detail::predicates::path<SegmentOrLinestring>
371 path(SegmentOrLinestring const& linestring, unsigned k)
373 return detail::predicates::path<SegmentOrLinestring>(linestring, k);
376 #endif // BOOST_GEOMETRY_INDEX_DETAIL_EXPERIMENTAL
378 namespace detail { namespace predicates {
380 // operator! generators
382 template <typename Fun, bool Negated> inline
383 satisfies<Fun, !Negated>
384 operator!(satisfies<Fun, Negated> const& p)
386 return satisfies<Fun, !Negated>(p);
389 template <typename Geometry, typename Tag, bool Negated> inline
390 spatial_predicate<Geometry, Tag, !Negated>
391 operator!(spatial_predicate<Geometry, Tag, Negated> const& p)
393 return spatial_predicate<Geometry, Tag, !Negated>(p.geometry);
396 // operator&& generators
398 template <typename Pred1, typename Pred2> inline
399 std::tuple<Pred1, Pred2>
400 operator&&(Pred1 const& p1, Pred2 const& p2)
402 /*typedef std::conditional_t<is_predicate<Pred1>::value, Pred1, Pred1 const&> stored1;
403 typedef std::conditional_t<is_predicate<Pred2>::value, Pred2, Pred2 const&> stored2;*/
404 return std::tuple<Pred1, Pred2>(p1, p2);
407 template <typename ...Preds, typename Pred> inline
408 typename geometry::tuples::push_back
410 std::tuple<Preds...>, Pred
412 operator&&(std::tuple<Preds...> const& t, Pred const& p)
414 //typedef std::conditional_t<is_predicate<Pred>::value, Pred, Pred const&> stored;
415 return geometry::tuples::push_back
417 std::tuple<Preds...>, Pred
421 }} // namespace detail::predicates
423 }}} // namespace boost::geometry::index
425 #endif // BOOST_GEOMETRY_INDEX_PREDICATES_HPP