libosmscout  1.1.1
GenCoordDat.h
Go to the documentation of this file.
1 #ifndef OSMSCOUT_IMPORT_GENCOORDDATA_H
2 #define OSMSCOUT_IMPORT_GENCOORDDATA_H
3 
4 /*
5  This source is part of the libosmscout library
6  Copyright (C) 2016 Tim Teulings
7 
8  This library is free software; you can redistribute it and/or
9  modify it under the terms of the GNU Lesser General Public
10  License as published by the Free Software Foundation; either
11  version 2.1 of the License, or (at your option) any later version.
12 
13  This library is distributed in the hope that it will be useful,
14  but WITHOUT ANY WARRANTY; without even the implied warranty of
15  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16  Lesser General Public License for more details.
17 
18  You should have received a copy of the GNU Lesser General Public
19  License along with this library; if not, write to the Free Software
20  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
21 */
22 
23 #include <map>
24 #include <vector>
25 
26 #include <osmscout/import/Import.h>
28 
30 
31 namespace osmscout {
32 
33  class SerialIdManager CLASS_FINAL
34  {
35  private:
36  // It seems, like a map is faster in this case then a default-initialized unordered_map
37  std::map<Id,uint8_t> idToSerialMap;
38 
39  public:
40  void MarkIdAsDuplicate(Id id);
41  uint8_t GetNextSerialForId(Id id);
42  size_t Size() const;
43  };
44 
45  template<typename I, typename E>
47  {
48  private:
49  std::map<I,std::vector<E>> pages;
50  uint32_t maximumEntriesInMemory;
51  uint32_t pageSize;
52  uint32_t overallEntryCount; // number of entries in file
53  std::function<void(const I&,std::vector<E>&&)> processor;
54  I minPageId;
55  I maxPageId;
56  uint32_t processedPagesCount;
57  uint32_t processedPagesEntryCount; // number of entries in completely processed pages
58  uint32_t handledPagesEntryCount; // number entries in current pages
59 
60  public:
61  PageManager(uint32_t maximumEntriesInMemory,
62  uint32_t pageSize,
63  uint32_t overallEntryCount,
64  std::function<void(const I&,std::vector<E>&&)> processor)
65  : maximumEntriesInMemory(maximumEntriesInMemory),
66  pageSize(pageSize),
67  overallEntryCount(overallEntryCount),
68  processor(processor),
69  minPageId(std::numeric_limits<I>::min()/static_cast<I>(pageSize)),
70  maxPageId(std::numeric_limits<I>::max()/static_cast<I>(pageSize)),
71  processedPagesCount(0u),
72  processedPagesEntryCount(0u),
73  handledPagesEntryCount(0u)
74  {
75  }
76 
77  I GetMinPageId() const {
78  return minPageId;
79  }
80 
81  uint32_t GetProcessedPagesCount() const
82  {
83  return processedPagesCount;
84  }
85 
86  uint32_t GetProcessedPagesEntryCount() const
87  {
88  return processedPagesEntryCount;
89  }
90 
91  bool IsACurrentlyHandledPage(const I& id) const
92  {
93  I pageId=id/pageSize;
94 
95  return pageId>=minPageId && pageId<=maxPageId;
96  }
97 
98  void AddEntry(const I& id, const E& entry)
99  {
100  I pageId=id/pageSize;
101 
102  pages[pageId].push_back(entry);
103  handledPagesEntryCount++;
104 
105  if (handledPagesEntryCount<maximumEntriesInMemory ||
106  pages.size()<=1) {
107  return;
108  }
109 
110  [[maybe_unused]] I oldMaxPageId=maxPageId;
111 
112  while (handledPagesEntryCount>maximumEntriesInMemory
113  && pages.size()>1) {
114  auto pageEntry=pages.rbegin();
115  I currentMaxPageId=pageEntry->first;
116 
117  handledPagesEntryCount-=(uint32_t)pageEntry->second.size();
118  pages.erase(currentMaxPageId);
119  maxPageId=currentMaxPageId-1;
120  }
121 
122  assert(maxPageId<=oldMaxPageId);
123  }
124 
125  bool AreAllEntriesLoaded() const
126  {
127  return processedPagesEntryCount+handledPagesEntryCount==overallEntryCount;
128  }
129 
131  {
132  processedPagesEntryCount+=handledPagesEntryCount;
133 
134  for (auto& pageEntry : pages) {
135  processor(pageEntry.first,std::move(pageEntry.second));
136  processedPagesCount++;
137  }
138 
139  handledPagesEntryCount=0;
140  pages.clear();
141  minPageId=maxPageId+1;
142  maxPageId=std::numeric_limits<OSMId>::max()/pageSize;
143  }
144  };
145 
146  template<typename I, typename E>
148  {
149  private:
150  size_t pageSize; //< Size of page
151  I currentPageId; //< Id of current page
152  size_t entryCount; //< Number of entries in the current page
153  size_t processedPagesCount; //< Number of processed pages
154  std::vector<E> page; //< Page data itself
155  std::function<void(const I&,std::vector<E>&)> processor; //< Callback for processing a complete page
156 
157  private:
158  void FlushPage()
159  {
160  processor(currentPageId,page);
161  InitializePage();
162 
163  processedPagesCount++;
164  }
165 
166  void InitializePage()
167  {
168  std::for_each(page.begin(),page.end(),[](E& entry) {
169  entry.isSet=false;
170  });
171 
172  entryCount=0;
173  }
174 
175  public:
176  PageSplitter(size_t pageSize,
177  std::function<void(const I&,std::vector<E>&)> processor)
178  : pageSize(pageSize),
179  currentPageId(std::numeric_limits<I>::min()),
180  entryCount(0),
181  processedPagesCount(0),
182  page(pageSize),
183  processor(processor)
184  {
185  }
186 
187  void Set(const I& id, const E& value)
188  {
189  I relatedId=std::numeric_limits<I>::min()+id;
190  I pageId=relatedId/pageSize;
191  I index=relatedId%pageSize;
192 
193  if (pageId!=currentPageId) {
194  if (entryCount>0) {
195  FlushPage();
196  }
197 
198  currentPageId=pageId;
199  }
200 
201  page[index]=value;
202  entryCount++;
203  }
204 
206  {
207  if (entryCount>0) {
208  FlushPage();
209  }
210  }
211 
212  size_t GetProcessedPagesCount() const
213  {
214  return processedPagesCount;
215  }
216  };
217 
218  class CoordDataGenerator CLASS_FINAL : public ImportModule
219  {
220  private:
221  bool FindDuplicateCoordinates(const TypeConfig& typeConfig,
222  const ImportParameter& parameter,
223  Progress& progress,
224  SerialIdManager& serialIdManager) const;
225 
226  bool StoreCoordinates(const TypeConfig& typeConfig,
227  const ImportParameter& parameter,
228  Progress& progress,
229  SerialIdManager& serialIdManager) const;
230 
231  public:
232  void GetDescription(const ImportParameter& parameter,
233  ImportModuleDescription& description) const override;
234 
235  bool Import(const TypeConfigRef& typeConfig,
236  const ImportParameter& parameter,
237  Progress& progress) override;
238  };
239 }
240 
241 #endif
uint32_t GetProcessedPagesEntryCount() const
Definition: GenCoordDat.h:86
uint64_t Id
Definition: OSMScoutTypes.h:41
I GetMinPageId() const
Definition: GenCoordDat.h:77
STL namespace.
void AddEntry(const I &id, const E &entry)
Definition: GenCoordDat.h:98
uint32_t GetProcessedPagesCount() const
Definition: GenCoordDat.h:81
PageSplitter(size_t pageSize, std::function< void(const I &, std::vector< E > &)> processor)
Definition: GenCoordDat.h:176
size_t GetProcessedPagesCount() const
Definition: GenCoordDat.h:212
void FileCompletelyScanned()
Definition: GenCoordDat.h:205
Definition: Area.h:38
#define CLASS_FINAL
Definition: Compiler.h:26
bool AreAllEntriesLoaded() const
Definition: GenCoordDat.h:125
PageManager(uint32_t maximumEntriesInMemory, uint32_t pageSize, uint32_t overallEntryCount, std::function< void(const I &, std::vector< E > &&)> processor)
Definition: GenCoordDat.h:61
bool IsACurrentlyHandledPage(const I &id) const
Definition: GenCoordDat.h:91
Definition: GenCoordDat.h:46
std::shared_ptr< TypeConfig > TypeConfigRef
Definition: TypeConfig.h:1227
Definition: GenCoordDat.h:147
void FileCompletelyScanned()
Definition: GenCoordDat.h:130
void Set(const I &id, const E &value)
Definition: GenCoordDat.h:187