1 #ifndef OSMIUM_RELATIONS_COLLECTOR_HPP 2 #define OSMIUM_RELATIONS_COLLECTOR_HPP 55 #include <osmium/relations/detail/relation_meta.hpp> 56 #include <osmium/relations/detail/member_meta.hpp> 100 template <
typename TCollector,
bool TNodes,
bool TWays,
bool TRelations>
113 m_collector(collector) {
117 if (m_collector.keep_relation(relation)) {
118 m_collector.add_relation(relation);
136 m_collector(collector) {
141 if (! m_collector.find_and_add_object(node)) {
142 m_collector.node_not_in_any_relation(node);
149 if (! m_collector.find_and_add_object(way)) {
150 m_collector.way_not_in_any_relation(way);
157 if (! m_collector.find_and_add_object(relation)) {
158 m_collector.relation_not_in_any_relation(relation);
190 int m_count_complete = 0;
195 static constexpr
size_t initial_buffer_size = 1024 * 1024;
198 auto& mmv = member_meta(type);
199 return make_range(std::equal_range(mmv.begin(), mmv.end(), MemberMeta(
id)));
208 m_handler_pass2(*static_cast<TCollector*>(this)),
209 m_relations_buffer(initial_buffer_size,
osmium::memory::Buffer::auto_grow::yes),
210 m_members_buffer(initial_buffer_size,
osmium::memory::Buffer::auto_grow::yes),
218 return m_member_meta[
static_cast<uint16_t
>(
type) - 1];
306 std::remove_if(m_relations.begin(), m_relations.end(), has_all_members()),
312 assert(m_relations_buffer.
committed() > offset);
320 return get_relation(relation_meta.relation_offset());
327 return get_relation(m_relations[member_meta.relation_pos()]);
331 assert(m_members_buffer.
committed() > offset);
346 const size_t offset = m_relations_buffer.
committed();
347 m_relations_buffer.
add_item(relation);
349 RelationMeta relation_meta(offset);
353 if (static_cast<TCollector*>(
this)->keep_member(relation_meta, member)) {
354 member_meta(member.type()).emplace_back(member.ref(), m_relations.size(), n);
355 relation_meta.increment_need_members();
362 assert(offset == m_relations_buffer.
committed());
363 if (relation_meta.has_all_members()) {
366 m_relations_buffer.
commit();
367 m_relations.push_back(std::move(relation_meta));
376 std::sort(m_member_meta[0].
begin(), m_member_meta[0].
end());
377 std::sort(m_member_meta[1].
begin(), m_member_meta[1].
end());
378 std::sort(m_member_meta[2].
begin(), m_member_meta[2].
end());
382 return std::count_if(range.
begin(), range.
end(), [](MemberMeta& mm) {
383 return !mm.removed();
395 auto range = find_member_meta(
object.
type(),
object.
id());
397 if (count_not_removed(range) == 0) {
403 members_buffer().add_item(
object);
404 const size_t member_offset = members_buffer().commit();
406 for (
auto& member_meta : range) {
407 member_meta.set_buffer_offset(member_offset);
411 for (
auto& member_meta : range) {
412 if (member_meta.removed()) {
415 assert(member_meta.member_id() ==
object.id());
416 assert(member_meta.relation_pos() < m_relations.size());
417 RelationMeta& relation_meta = m_relations[member_meta.relation_pos()];
418 assert(member_meta.member_pos() < get_relation(relation_meta).members().size());
419 relation_meta.got_one_member();
420 if (relation_meta.has_all_members()) {
421 const size_t relation_offset = member_meta.relation_pos();
422 static_cast<TCollector*
>(
this)->complete_relation(relation_meta);
423 clear_member_metas(relation_meta);
424 m_relations[relation_offset] = RelationMeta();
425 possibly_purge_removed_members();
434 for (
const auto& member : relation.
members()) {
435 if (member.ref() != 0) {
436 const auto range = find_member_meta(member.type(), member.ref());
437 assert(!range.empty());
441 if (count_not_removed(range) == 1) {
442 get_member(range.begin()->buffer_offset()).set_removed(
true);
445 for (
auto& member_meta : range) {
446 if (!member_meta.removed() && relation.
id() == get_relation(member_meta).id()) {
447 member_meta.remove();
458 const uint64_t nmembers = m_member_meta[0].capacity() + m_member_meta[1].capacity() + m_member_meta[2].capacity();
459 const uint64_t members = nmembers *
sizeof(MemberMeta);
460 const uint64_t relations = m_relations.capacity() *
sizeof(RelationMeta);
461 const uint64_t relations_buffer_capacity = m_relations_buffer.
capacity();
462 const uint64_t members_buffer_capacity = m_members_buffer.
capacity();
464 std::cerr <<
" nR = m_relations.capacity() ........... = " << std::setw(12) << m_relations.capacity() <<
"\n";
465 std::cerr <<
" nMN = m_member_meta[NODE].capacity() ... = " << std::setw(12) << m_member_meta[0].capacity() <<
"\n";
466 std::cerr <<
" nMW = m_member_meta[WAY].capacity() .... = " << std::setw(12) << m_member_meta[1].capacity() <<
"\n";
467 std::cerr <<
" nMR = m_member_meta[RELATION].capacity() = " << std::setw(12) << m_member_meta[2].capacity() <<
"\n";
468 std::cerr <<
" nM = m_member_meta[*].capacity() ...... = " << std::setw(12) << nmembers <<
"\n";
470 std::cerr <<
" sRM = sizeof(RelationMeta) ............. = " << std::setw(12) <<
sizeof(RelationMeta) <<
"\n";
471 std::cerr <<
" sMM = sizeof(MemberMeta) ............... = " << std::setw(12) <<
sizeof(MemberMeta) <<
"\n\n";
473 std::cerr <<
" nR * sRM ............................... = " << std::setw(12) << relations <<
"\n";
474 std::cerr <<
" nM * sMM ............................... = " << std::setw(12) << members <<
"\n";
475 std::cerr <<
" relations_buffer_capacity .............. = " << std::setw(12) << relations_buffer_capacity <<
"\n";
476 std::cerr <<
" members_buffer_capacity ................ = " << std::setw(12) << members_buffer_capacity <<
"\n";
478 const uint64_t total = relations + members + relations_buffer_capacity + members_buffer_capacity;
480 std::cerr <<
" total .................................. = " << std::setw(12) << total <<
"\n";
481 std::cerr <<
" =======================================================\n";
483 return relations_buffer_capacity + members_buffer_capacity + relations + members;
490 m_callback = callback;
491 return m_handler_pass2;
495 return m_members_buffer;
510 const auto range = find_member_meta(type,
id);
511 assert(!range.empty());
512 return range.begin()->is_available();
525 const auto range = find_member_meta(type,
id);
526 assert(!range.empty());
527 assert(range.begin()->is_available());
528 return range.begin()->buffer_offset();
548 const auto range = find_member_meta(type,
id);
549 assert(!range.empty());
550 if (range.begin()->is_available()) {
551 return std::make_pair(
true, range.begin()->buffer_offset());
553 return std::make_pair(
false, 0);
557 template <
typename TIter>
559 HandlerPass1 handler(*static_cast<TCollector*>(
this));
564 template <
typename TSource>
572 auto range = find_member_meta(
object.
type(),
object.
id());
573 for (
auto& member_meta : range) {
574 assert(member_meta.buffer_offset() == old_offset);
575 member_meta.set_buffer_offset(new_offset);
587 if (m_count_complete > 10000) {
597 m_count_complete = 0;
610 std::vector<const osmium::Relation*> relations;
611 for (
const auto& relation_meta : m_relations) {
612 if (!relation_meta.has_all_members()) {
613 relations.push_back(&get_relation(relation_meta));
625 #endif // OSMIUM_RELATIONS_COLLECTOR_HPP mm_vector_type::iterator mm_iterator
Definition: collector.hpp:187
void relation(const osmium::Relation &relation)
Definition: collector.hpp:155
void clear_member_metas(const osmium::relations::RelationMeta &relation_meta)
Definition: collector.hpp:432
Definition: iterator.hpp:43
callback_func_type m_callback
Definition: collector.hpp:193
osmium::memory::Buffer & members_buffer()
Definition: collector.hpp:494
osmium::OSMObject & get_member(size_t offset) const
Definition: collector.hpp:330
It begin() const
Definition: iterator.hpp:59
type
Definition: entity_bits.hpp:63
iterator_range< It > make_range(P &&p)
Definition: iterator.hpp:77
RelationMemberList & members()
Definition: relation.hpp:176
bool is_available(osmium::item_type type, osmium::object_id_type id)
Definition: collector.hpp:509
const std::vector< RelationMeta > & relations() const
Definition: collector.hpp:225
bool keep_relation(const osmium::Relation &) const
Definition: collector.hpp:238
void way(const osmium::Way &way)
Definition: collector.hpp:147
item_type
Definition: item_type.hpp:43
std::vector< const osmium::Relation * > get_incomplete_relations() const
Definition: collector.hpp:609
void clean_assembled_relations()
Definition: collector.hpp:304
void moving_in_buffer(size_t old_offset, size_t new_offset)
Definition: collector.hpp:570
Definition: relation.hpp:163
Definition: handler.hpp:71
osmium::memory::Buffer m_members_buffer
Definition: collector.hpp:177
void read_relations(TSource &source)
Definition: collector.hpp:565
bool keep_member(const osmium::relations::RelationMeta &, const osmium::RelationMember &) const
Definition: collector.hpp:252
size_t get_offset(osmium::item_type type, osmium::object_id_type id)
Definition: collector.hpp:524
void relation_not_in_any_relation(const osmium::Relation &)
Definition: collector.hpp:283
std::vector< MemberMeta > & member_meta(const item_type type)
Definition: collector.hpp:217
bool find_and_add_object(const osmium::OSMObject &object)
Definition: collector.hpp:394
Definition: collector.hpp:129
HandlerPass2(TCollector &collector) noexcept
Definition: collector.hpp:135
std::vector< RelationMeta > m_relations
Vector with all relations we are interested in.
Definition: collector.hpp:180
std::pair< bool, size_t > get_availability_and_offset(osmium::item_type type, osmium::object_id_type id)
Definition: collector.hpp:547
void sort_member_meta()
Definition: collector.hpp:375
void node_not_in_any_relation(const osmium::Node &)
Definition: collector.hpp:263
std::function< void(osmium::memory::Buffer &&)> callback_func_type
Definition: collector.hpp:192
Definition: relation.hpp:57
TCollector & m_collector
Definition: collector.hpp:108
Namespace for everything in the Osmium library.
Definition: assembler.hpp:73
T & add_item(const T &item)
Definition: buffer.hpp:482
Definition: collector.hpp:101
iterator_range< mm_iterator > find_member_meta(osmium::item_type type, osmium::object_id_type id)
Definition: collector.hpp:197
void purge_removed(TCallbackClass *callback)
Definition: buffer.hpp:730
HandlerPass2 m_handler_pass2
Definition: collector.hpp:171
Collector()
Definition: collector.hpp:207
const osmium::Relation & get_relation(const RelationMeta &relation_meta) const
Definition: collector.hpp:319
uint64_t used_memory() const
Definition: collector.hpp:457
size_t capacity() const noexcept
Definition: buffer.hpp:251
void relation(const osmium::Relation &relation)
Definition: collector.hpp:116
osmium::io::InputIterator< osmium::io::Reader > end(osmium::io::Reader &)
Definition: reader_iterator.hpp:45
Definition: collector.hpp:106
int64_t object_id_type
Type for OSM object (node, way, or relation) IDs.
Definition: types.hpp:45
void flush()
Definition: collector.hpp:163
std::vector< MemberMeta > mm_vector_type
Definition: collector.hpp:186
osmium::memory::Buffer m_relations_buffer
Definition: collector.hpp:174
void apply(TIterator it, TIterator end, THandlers &... handlers)
Definition: visitor.hpp:234
object_id_type id() const noexcept
Get ID of this object.
Definition: object.hpp:118
size_t committed() const noexcept
Definition: buffer.hpp:259
callback_func_type callback()
Definition: collector.hpp:221
Definition: buffer.hpp:97
void add_relation(const osmium::Relation &relation)
Definition: collector.hpp:345
HandlerPass2 & handler(const callback_func_type &callback=nullptr)
Definition: collector.hpp:489
void flush()
Definition: collector.hpp:297
void way_not_in_any_relation(const osmium::Way &)
Definition: collector.hpp:273
void node(const osmium::Node &node)
Definition: collector.hpp:139
void possibly_purge_removed_members()
Definition: collector.hpp:585
TCollector & m_collector
Definition: collector.hpp:131
void read_relations(TIter begin, TIter end)
Definition: collector.hpp:558
osmium::io::InputIterator< osmium::io::Reader > begin(osmium::io::Reader &reader)
Definition: reader_iterator.hpp:41
const osmium::Relation & get_relation(size_t offset) const
Definition: collector.hpp:311
HandlerPass1(TCollector &collector) noexcept
Definition: collector.hpp:112
void rollback()
Definition: buffer.hpp:370
T & get(const size_t offset) const
Definition: buffer.hpp:404
static iterator_range< mm_iterator >::iterator::difference_type count_not_removed(const iterator_range< mm_iterator > &range)
Definition: collector.hpp:381
It end() const
Definition: iterator.hpp:63
const osmium::Relation & get_relation(const MemberMeta &member_meta) const
Definition: collector.hpp:326
Definition: object.hpp:63
size_t commit()
Definition: buffer.hpp:354