@@ -269,36 +288,64 @@
std::vector<Value> values;
-
+
RTree rt1;
BOOST_FOREACH(Value const& v, values)
rt1.insert(v);
-
+
RTree rt2;
rt2.insert(values.begin(), values.end());
-
+
RTree rt3;
rt3.insert(values);
-
+
RTree rt4(values.begin(), values.end());
-
+
RTree rt5(values);
-
+
BOOST_FOREACH(Value const& v, values)
rt1.remove(v);
-
+
rt2.remove(values.begin(), values.end());
-
+
rt3.remove(values);
+
+
+
+ There are functions like std::copy(), or R-tree's queries that copy values
+ to an output iterator. In order to insert values to a container in this
+ kind of function insert iterators may be used. Geometry.Index provide its
+ own bgi::insert_iterator<Container>
+ which is generated by bgi::inserter() function.
+
+
namespace bgi = boost::geometry::index;
+typedef std::pair<Box, int> Value;
+typedef bgi::rtree< Value, bgi::linear<32, 8> > RTree;
+
+std::vector<Value> values;
+
+
+
+RTree rt1;
+std::copy(values.begin(), values.end(), bgi::inserter(rt1));
+
+
+RTree rt2;
+rt1.spatial_query(Box(/*...*/), bgi::inserter(rt2));
+
+
|
diff --git a/doc/html/geometry_index/r_tree/spatial_queries.html b/doc/html/geometry_index/r_tree/spatial_queries.html
index 6da37a16f..a26b1bcc2 100644
--- a/doc/html/geometry_index/r_tree/spatial_queries.html
+++ b/doc/html/geometry_index/r_tree/spatial_queries.html
@@ -35,6 +35,8 @@
predicates
Value
predicate
+Inserting
+ query results into the other R-tree
Spatial queries returns Values
@@ -211,6 +213,43 @@
std::back_inserter(result));
+
+
+
+ There are several ways of inserting Values returned by a query to the other
+ R-tree container. The most basic way is creating a temporary container
+ for Values and insert them later.
+
+
namespace bgi = boost::geometry::index;
+typedef std::pair<Box, int> Value;
+typedef bgi::rtree< Value, bgi::linear<32, 8> > RTree;
+
+RTree rt1;
+
+
+std::vector<Value> result;
+rt1.spatial_query(Box(/*...*/), std::back_inserter(result));
+RTree rt2(result.begin(), result.end());
+
+
+ However there are better ways. One of these methods is mentioned in the
+ "Creation and modification" section. The insert iterator may
+ be passed directly to the query, which will be the fastest way of inserting
+ query results because temporary container won't be used.
+
+
RTree rt3;
+rt1.spatial_query(Box(/*...*/), bgi::inserter(rt3));
+
+
+ If you like Boost.Range you'll appreciate the third option. You may pass
+ the result Range directly to the constructor.
+
+
RTree rt4(rt1 | bgi::adaptors::spatial_queried(Box(/*...*/)));
+
+
|
diff --git a/doc/html/index.html b/doc/html/index.html
index 16d52db19..ea9ad1961 100644
--- a/doc/html/index.html
+++ b/doc/html/index.html
@@ -56,7 +56,7 @@
-Last revised: November 26, 2012 at 17:58:58 GMT |
+Last revised: November 26, 2012 at 22:11:47 GMT |
|
diff --git a/doc/rtree/creation.qbk b/doc/rtree/creation.qbk
index 9a1393065..4a70e0ef3 100644
--- a/doc/rtree/creation.qbk
+++ b/doc/rtree/creation.qbk
@@ -51,9 +51,13 @@ A `__translator__` is a type which knows how to handle `__value__`s. It has two
A `__translator__` translates the `__value__` each time the __rtree__ needs it. For this reason
it should rather return const reference to the `__indexable__` than a copy.
-If comparison of two `__value__`s is required, the default translator compares
-both components of the `std::pair<...>`. If the second one is a `Geometry`,
-`geometry::equals()` function is used. For other types it uses `operator==()`.
+If comparison of two `__value__`s is required, the default translator:
+
+* for `__point__` and `__box__` - compares `__value__`s with geometry::equals().
+* for `std::pair<...>` - compares both components of the `__value__`. The first one is compared with `geometry::equals()`.
+ If the second one is a `Geometry`, `geometry::equals()` function is used. For other types it uses `operator==()`.
+* for `boost::tuple<...>` - compares all components of the `__value__`. If the component is a `Geometry`, `geometry::equals()`
+ function is used. For other types it uses `operator==()`.
[endsect]
@@ -165,35 +169,59 @@ The __rtree__ allows creation, inserting and removing of Values from a range. Th
std::vector<__value__> values;
/* vector filling code, here */
- // create a RTree with default constructor and insert values with RTree::insert(Value const&)
+ // create R-tree with default constructor and insert values with insert(Value const&)
RTree rt1;
BOOST_FOREACH(__value__ const& v, values)
rt1.insert(v);
- // create a RTree with default constructor and insert values with RTree::insert(Iter, Iter)
+ // create R-tree with default constructor and insert values with insert(Iter, Iter)
RTree rt2;
rt2.insert(values.begin(), values.end());
- // create a RTree with default constructor and insert values with RTree::insert(Range)
+ // create R-tree with default constructor and insert values with insert(Range)
RTree rt3;
rt3.insert(values);
- // create a RTree with constructor taking Iterators
+ // create R-tree with constructor taking Iterators
RTree rt4(values.begin(), values.end());
- // create a RTree with constructor taking Range
+ // create R-tree with constructor taking Range
RTree rt5(values);
- // remove values with RTree::remove(Value const&)
+ // remove values with remove(Value const&)
BOOST_FOREACH(__value__ const& v, values)
rt1.remove(v);
- // remove values with RTree::remove(Iter, Iter)
+ // remove values with remove(Iter, Iter)
rt2.remove(values.begin(), values.end());
- // remove values with RTree::remove(Range)
+ // remove values with remove(Range)
rt3.remove(values);
[endsect]
+[section Insert iterator]
+
+There are functions like `std::copy()`, or __rtree__'s queries that copy values to an output iterator.
+In order to insert values to a container in this kind of function insert iterators may be used.
+Geometry.Index provide its own `bgi::insert_iterator` which is generated by
+`bgi::inserter()` function.
+
+ namespace bgi = boost::geometry::index;
+ typedef std::pair __value__;
+ typedef bgi::rtree< __value__, bgi::linear<32, 8> > RTree;
+
+ std::vector<__value__> values;
+ /* vector filling code, here */
+
+ // create R-tree and insert values from the vector
+ RTree rt1;
+ std::copy(values.begin(), values.end(), bgi::inserter(rt1));
+
+ // create R-tree and insert values returned by a query
+ RTree rt2;
+ rt1.spatial_query(Box(/*...*/), bgi::inserter(rt2));
+
+[endsect]
+
[endsect] [/ Creation and modification /]
diff --git a/doc/rtree/spatial_query.qbk b/doc/rtree/spatial_query.qbk
index e9802a977..562555444 100644
--- a/doc/rtree/spatial_query.qbk
+++ b/doc/rtree/spatial_query.qbk
@@ -104,4 +104,34 @@ which checks if `__value__` should be returned by the query.
[endsect]
+[section Inserting query results into the other R-tree]
+
+There are several ways of inserting Values returned by a query to the other R-tree container.
+The most basic way is creating a temporary container for Values and insert them later.
+
+ namespace bgi = boost::geometry::index;
+ typedef std::pair __value__;
+ typedef bgi::rtree< __value__, bgi::linear<32, 8> > RTree;
+
+ RTree rt1;
+ /* some inserting into the tree */
+
+ std::vector result;
+ rt1.spatial_query(Box(/*...*/), std::back_inserter(result));
+ RTree rt2(result.begin(), result.end());
+
+However there are better ways. One of these methods is mentioned in the "Creation and modification" section.
+The insert iterator may be passed directly to the query, which will be the fastest way of inserting
+query results because temporary container won't be used.
+
+ RTree rt3;
+ rt1.spatial_query(Box(/*...*/), bgi::inserter(rt3));
+
+If you like Boost.Range you'll appreciate the third option. You may pass the result Range directly to the
+constructor.
+
+ RTree rt4(rt1 | bgi::adaptors::spatial_queried(Box(/*...*/)));
+
+[endsect]
+
[endsect] [/ Spatial queries /]
diff --git a/include/boost/geometry/extensions/index/inserter.hpp b/include/boost/geometry/extensions/index/inserter.hpp
index 15f4b176b..186d62f9a 100644
--- a/include/boost/geometry/extensions/index/inserter.hpp
+++ b/include/boost/geometry/extensions/index/inserter.hpp
@@ -22,17 +22,13 @@ class insert_iterator :
public:
typedef Container container_type;
- inline explicit insert_iterator()
-// : container(0)
- {}
-
inline explicit insert_iterator(Container & c)
- : container(&c)
+ : container(c)
{}
insert_iterator & operator=(typename Container::value_type const& value)
{
- index::insert(*container, value);
+ container.insert(value);
return *this;
}
@@ -52,7 +48,7 @@ public:
}
private:
- Container * container;
+ Container & container;
};
template
diff --git a/include/boost/geometry/extensions/index/rtree/rtree.hpp b/include/boost/geometry/extensions/index/rtree/rtree.hpp
index 349d0ca77..dc2946fcc 100644
--- a/include/boost/geometry/extensions/index/rtree/rtree.hpp
+++ b/include/boost/geometry/extensions/index/rtree/rtree.hpp
@@ -45,6 +45,8 @@
#include
//#include
+#include
+
// TODO change the name to bounding_tree
namespace boost { namespace geometry { namespace index {
diff --git a/test/rtree/test_rtree.hpp b/test/rtree/test_rtree.hpp
index a40e6f716..4bd8d77a5 100644
--- a/test/rtree/test_rtree.hpp
+++ b/test/rtree/test_rtree.hpp
@@ -676,6 +676,14 @@ void test_create_insert(bgi::rtree & tree, std::vector const
t.spatial_query(qbox, std::back_inserter(output));
test_exactly_the_same_outputs(t, output, expected_output);
}
+ {
+ T t(tree.parameters());
+ std::copy(input.begin(), input.end(), bgi::inserter(t));
+ BOOST_CHECK(tree.size() == t.size());
+ std::vector output;
+ t.spatial_query(qbox, std::back_inserter(output));
+ test_exactly_the_same_outputs(t, output, expected_output);
+ }
{
T t(input.begin(), input.end(), tree.parameters());
BOOST_CHECK(tree.size() == t.size());