libLAS API Reference  1.8.1
index.hpp
Go to the documentation of this file.
1 /******************************************************************************
2  * $Id$
3  *
4  * Project: libLAS - http://liblas.org - A BSD library for LAS format data.
5  * Purpose: LAS index class
6  * Author: Gary Huber, gary@garyhuberart.com
7  *
8  ******************************************************************************
9  * Copyright (c) 2010, Gary Huber, gary@garyhuberart.com
10  *
11  * All rights reserved.
12  *
13  * Redistribution and use in source and binary forms, with or without
14  * modification, are permitted provided that the following
15  * conditions are met:
16  *
17  * * Redistributions of source code must retain the above copyright
18  * notice, this list of conditions and the following disclaimer.
19  * * Redistributions in binary form must reproduce the above copyright
20  * notice, this list of conditions and the following disclaimer in
21  * the documentation and/or other materials provided
22  * with the distribution.
23  * * Neither the name of the Martin Isenburg or Iowa Department
24  * of Natural Resources nor the names of its contributors may be
25  * used to endorse or promote products derived from this software
26  * without specific prior written permission.
27  *
28  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
29  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
30  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
31  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
32  * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
33  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
34  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
35  * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
36  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
37  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
38  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
39  * OF SUCH DAMAGE.
40  ****************************************************************************/
41 
42 #ifndef LIBLAS_LASINDEX_HPP_INCLUDED
43 #define LIBLAS_LASINDEX_HPP_INCLUDED
44 
45 #include <liblas/reader.hpp>
46 #include <liblas/header.hpp>
47 #include <liblas/bounds.hpp>
49 #include <liblas/detail/index/indexcell.hpp>
50 #include <liblas/export.hpp>
51 
52 // std
53 #include <stdexcept> // std::out_of_range
54 #include <cstdio> // file io
55 #include <iostream> // file io
56 #include <cstdlib> // std::size_t
57 #include <vector> // std::vector
58 
59 namespace liblas {
60 
61 #define LIBLAS_INDEX_MAXMEMDEFAULT 10000000 // 10 megs default
62 #define LIBLAS_INDEX_MINMEMDEFAULT 1000000 // 1 meg at least has to be allowed
63 #define LIBLAS_INDEX_VERSIONMAJOR 1
64 #define LIBLAS_INDEX_VERSIONMINOR 2 // minor version 2 begins 11/15/10
65 #define LIBLAS_INDEX_MAXSTRLEN 512
66 #define LIBLAS_INDEX_MAXCELLS 250000
67 #define LIBLAS_INDEX_OPTPTSPERCELL 100
68 #define LIBLAS_INDEX_MAXPTSPERCELL 1000
69 #define LIBLAS_INDEX_RESERVEFILTERDEFAULT 1000000 // 1 million points will be reserved on large files for filter result
70 
71 // define this in order to fix problem with last bytes of last VLR getting corrupted
72 // when saved and reloaded from index or las file.
73 #define LIBLAS_INDEX_PADLASTVLR
74 
75 typedef std::vector<uint8_t> IndexVLRData;
76 typedef std::vector<liblas::detail::IndexCell> IndexCellRow;
77 typedef std::vector<IndexCellRow> IndexCellDataBlock;
78 
81 
82 // Index class is the fundamental object for building and filtering a spatial index of points in an LAS file.
83 // An Index class doesn't do anything until it is configured with an IndexData object (see below).
84 // You instantiate an Index object first and then pass it an IndexData or you can construct the Index with an
85 // IndexData. Nothing happens until the Index is told what to do via the configuration with IndexData.
86 // For details on configuration options see IndexData below.
87 
88 // Once an index exists and is configured, it can be used to filter the point set in the LAS file for which it
89 // was built. The points have to be what they were when the index was built. The index is not automatically
90 // updated if the point set is changed. The index becomes invalid if either the number of points is changed,
91 // the order of points is changed or the location of any points is changed. The Validate function is run to
92 // determine as best it can the validity of the stored index but it isn't perfect. It can only determine if
93 // the number of points has changed or the spatial extents of the file have changed.
94 
95 // The user can constrain the memory used in building an index if that is believed to be an issue.
96 // The results will be the same but some efficiency may be lost in the index building process.
97 
98 // Data stored in index header can be examined for determining suitability of index for desired purpose.
99 // 1) presence of z-dimensional cell structure is indicated by GetCellsZ() called on the Index.
100 // 2) Index author GetIndexAuthorStr() - provided by author at time of creation
101 // 3) Index comment GetIndexCommentStr() - provided by author at time of creation
102 // 4) Index creation date GetIndexDateStr() - provided by author at time of creation
103 // The latter fields are not validated in any way by the index building code and are just three fields
104 // which can be used as the user sees fit. Maximum length is LIBLAS_INDEX_MAXSTRLEN - 1.
105 
106 // Obtaining a filtered set of points requires that a valid index exist (see above).
107 // The IndexData class is used again to pass the extents of the filter to the Index. By making any high/low
108 // bounds coordinate pair equal, that dimension is ignored for the purposes of filtering. Note that Z dimension
109 // discrimination is still available even if z-binning was not invoked during index creation. Filtering with
110 // the z dimension may be slower in that event but no less successful.
111 
112 // A filter operation is invoked with the command:
113 // const std::vector<uint32_t>& Filter(IndexData const& ParamSrc);
114 // The return value is a vector of point ID's. The points can be accessed from the LAS file in the standard way
115 // as the index in no way modifies them or their sequential order.
116 // Currently only one, two or three dimensional spatial window filters are supported. See IndexData below for
117 // more info on filtering.
118 
120 {
121 public:
122  Index();
123  Index(IndexData const& ParamSrc);
124  ~Index();
125 
126  // Blocked copying operations, declared but not defined.
128  Index(Index const& other);
130  Index& operator=(Index const& rhs);
131 
132 private:
133 
134  Reader *m_reader;
135  Reader *m_idxreader;
136  Header m_pointheader;
137  Header m_idxheader;
138  Bounds<double> m_bounds;
139  bool m_indexBuilt, m_tempFileStarted, m_readerCreated, m_readOnly, m_writestandaloneindex, m_forceNewIndex;
140  int m_debugOutputLevel;
141  uint8_t m_versionMajor, m_versionMinor;
142  uint32_t m_pointRecordsCount, m_maxMemoryUsage, m_cellsX, m_cellsY, m_cellsZ, m_totalCells,
143  m_DataVLR_ID;
144  liblas::detail::TempFileOffsetType m_tempFileWrittenBytes;
145  double m_rangeX, m_rangeY, m_rangeZ, m_cellSizeZ, m_cellSizeX, m_cellSizeY;
146  std::string m_tempFileName;
147  std::string m_indexAuthor;
148  std::string m_indexComment;
149  std::string m_indexDate;
150  std::vector<uint32_t> m_filterResult;
151  std::ostream *m_ofs;
152  FILE *m_tempFile, *m_outputFile;
153  FILE *m_debugger;
154 
155  void SetValues(void);
156  bool IndexInit(void);
157  void ClearOldIndex(void);
158  bool BuildIndex(void);
159  bool Validate(void);
160  uint32_t GetDefaultReserve(void);
161  bool LoadIndexVLR(VariableRecord const& vlr);
162  void SetCellFilterBounds(IndexData & ParamSrc);
163  bool FilterOneVLR(VariableRecord const& vlr, uint32_t& i, IndexData & ParamSrc, bool & VLRDone);
164  bool FilterPointSeries(uint32_t & PointID, uint32_t & PointsScanned,
165  uint32_t const PointsToIgnore, uint32_t const x, uint32_t const y, uint32_t const z,
166  liblas::detail::ConsecPtAccumulator const ConsecutivePts, IndexIterator *Iterator,
167  IndexData const& ParamSrc);
168  bool VLRInteresting(int32_t MinCellX, int32_t MinCellY, int32_t MaxCellX, int32_t MaxCellY,
169  IndexData const& ParamSrc);
170  bool CellInteresting(int32_t x, int32_t y, IndexData const& ParamSrc);
171  bool SubCellInteresting(int32_t SubCellID, int32_t XCellID, int32_t YCellID, IndexData const& ParamSrc);
172  bool ZCellInteresting(int32_t ZCellID, IndexData const& ParamSrc);
173  bool FilterOnePoint(int32_t x, int32_t y, int32_t z, int32_t PointID, int32_t LastPointID, bool &LastPtRead,
174  IndexData const& ParamSrc);
175  // Determines what X/Y cell in the basic cell matrix a point falls in
176  bool IdentifyCell(Point const& CurPt, uint32_t& CurCellX, uint32_t& CurCellY) const;
177  // determines what Z cell a point falls in
178  bool IdentifyCellZ(Point const& CurPt, uint32_t& CurCellZ) const;
179  // Determines what quadrant sub-cell a point falls in
180  bool IdentifySubCell(Point const& CurPt, uint32_t x, uint32_t y, uint32_t& CurSubCell) const;
181  // Offloads binned cell data while building Index when cell data in memory exceeds maximum set by user
182  bool PurgePointsToTempFile(IndexCellDataBlock& CellBlock);
183  // Reloads and examines one cell of data from temp file
184  bool LoadCellFromTempFile(liblas::detail::IndexCell *CellBlock,
185  uint32_t CurCellX, uint32_t CurCellY);
186  // temp file is used to store sorted data while building index
187  FILE *OpenTempFile(void);
188  // closes and removes the temp file
189  void CloseTempFile(void);
190  // Creates a Writer from m_ofs and re-saves entire LAS input file with new index
191  // Current version does not save any data following the points
192  bool SaveIndexInLASFile(void);
193  // Creates a Writer from m_ofs and re-saves LAS header with new index, but not with data point records
194  bool SaveIndexInStandAloneFile(void);
195  // Calculate index bounds dimensions
196  void CalcRangeX(void) {m_rangeX = (m_bounds.max)(0) - (m_bounds.min)(0);}
197  void CalcRangeY(void) {m_rangeY = (m_bounds.max)(1) - (m_bounds.min)(1);}
198  void CalcRangeZ(void) {m_rangeZ = (m_bounds.max)(2) - (m_bounds.min)(2);}
199 
200  // error messages
201  bool FileError(const char *Reporter);
202  bool InputFileError(const char *Reporter) const;
203  bool OutputFileError(const char *Reporter) const;
204  bool DebugOutputError(const char *Reporter) const;
205  bool PointCountError(const char *Reporter) const;
206  bool PointBoundsError(const char *Reporter) const;
207  bool MemoryError(const char *Reporter) const;
208  bool InitError(const char *Reporter) const;
209  bool InputBoundsError(const char *Reporter) const;
210 
211  // debugging
212  bool OutputCellStats(IndexCellDataBlock& CellBlock) const;
213  bool OutputCellGraph(std::vector<uint32_t> CellPopulation, uint32_t MaxPointsPerCell) const;
214 
215 public:
216  // IndexFailed and IndexReady can be used to tell if an Index is ready for a filter operation
217  bool IndexFailed(void) const {return (! m_indexBuilt);}
218  bool IndexReady(void) const {return (m_indexBuilt);}
219  // Prep takes the input data and initializes Index values and then either builds or examines the Index
220  bool Prep(IndexData const& ParamSrc);
221  // Filter performs a point filter using the bounds in ParamSrc
222  const std::vector<uint32_t>& Filter(IndexData & ParamSrc);
223  IndexIterator* Filter(IndexData const& ParamSrc, uint32_t ChunkSize);
224  IndexIterator* Filter(double LowFilterX, double HighFilterX, double LowFilterY, double HighFilterY,
225  double LowFilterZ, double HighFilterZ, uint32_t ChunkSize);
226  IndexIterator* Filter(Bounds<double> const& BoundsSrc, uint32_t ChunkSize);
227 
228  // Return the bounds of the current Index
229  double GetMinX(void) const {return (m_bounds.min)(0);}
230  double GetMaxX(void) const {return (m_bounds.max)(0);}
231  double GetMinY(void) const {return (m_bounds.min)(1);}
232  double GetMaxY(void) const {return (m_bounds.max)(1);}
233  double GetMinZ(void) const {return (m_bounds.min)(2);}
234  double GetMaxZ(void) const {return (m_bounds.max)(2);}
235  // Ranges are updated when an index is built or the index header VLR read
236  double GetRangeX(void) const {return m_rangeX;}
237  double GetRangeY(void) const {return m_rangeY;}
238  double GetRangeZ(void) const {return m_rangeZ;}
239  Bounds<double> const& GetBounds(void) const {return m_bounds;}
240  // Return the number of points used to build the Index
241  uint32_t GetPointRecordsCount(void) const {return m_pointRecordsCount;}
242  // Return the number of cells in the Index
243  uint32_t GetCellsX(void) const {return m_cellsX;}
244  uint32_t GetCellsY(void) const {return m_cellsY;}
245  // Return the number of Z-dimension cells in the Index. Value is 1 if no Z-cells were created during Index building
246  uint32_t GetCellsZ(void) const {return m_cellsZ;}
247  // 42 is the ID for the Index header VLR and 43 is the normal ID for the Index data VLR's
248  // For future expansion, multiple indexes could assign data VLR ID's of their own choosing
249  uint32_t GetDataVLR_ID(void) const {return m_DataVLR_ID;}
250  // Since the user can define a Z cell size it is useful to examine that for an existing index
251  double GetCellSizeZ(void) const {return m_cellSizeZ;}
252  // Return values used in building or examining index
253  FILE *GetDebugger(void) const {return m_debugger;}
254  bool GetReadOnly(void) const {return m_readOnly;}
255  bool GetStandaloneIndex(void) const {return m_writestandaloneindex;}
256  bool GetForceNewIndex(void) const {return m_forceNewIndex;}
257  uint32_t GetMaxMemoryUsage(void) const {return m_maxMemoryUsage;}
258  int GetDebugOutputLevel(void) const {return m_debugOutputLevel;}
259  // Not sure if these are more useful than dangerous
260  Header *GetPointHeader(void) {return &m_pointheader;}
261  Header *GetIndexHeader(void) {return &m_idxheader;}
262  Reader *GetReader(void) const {return m_reader;}
263  Reader *GetIndexReader(void) const {return m_idxreader;}
264  const char *GetTempFileName(void) const {return m_tempFileName.c_str();}
265  // Returns the strings set in the index when built
266  const char *GetIndexAuthorStr(void) const;
267  const char *GetIndexCommentStr(void) const;
268  const char *GetIndexDateStr(void) const;
269  uint8_t GetVersionMajor(void) const {return m_versionMajor;}
270  uint8_t GetVersionMinor(void) const {return m_versionMinor;}
271  // Methods for setting values used when reading index from file to facilitate moving reading function into
272  // separate IndexInput object at a future time to provide symmetry with IndexOutput
273  void SetDataVLR_ID(uint32_t DataVLR_ID) {m_DataVLR_ID = DataVLR_ID;}
274  void SetIndexAuthorStr(const char *ias) {m_indexAuthor = ias;}
275  void SetIndexCommentStr(const char *ics) {m_indexComment = ics;}
276  void SetIndexDateStr(const char *ids) {m_indexDate = ids;}
277  void SetMinX(double minX) {(m_bounds.min)(0, minX);}
278  void SetMaxX(double maxX) {(m_bounds.max)(0, maxX);}
279  void SetMinY(double minY) {(m_bounds.min)(1, minY);}
280  void SetMaxY(double maxY) {(m_bounds.max)(1, maxY);}
281  void SetMinZ(double minZ) {(m_bounds.min)(2, minZ);}
282  void SetMaxZ(double maxZ) {(m_bounds.max)(2, maxZ);}
283  void SetPointRecordsCount(uint32_t prc) {m_pointRecordsCount = prc;}
284  void SetCellsX(uint32_t cellsX) {m_cellsX = cellsX;}
285  void SetCellsY(uint32_t cellsY) {m_cellsY = cellsY;}
286  void SetCellsZ(uint32_t cellsZ) {m_cellsZ = cellsZ;}
287 
288 };
289 
290 // IndexData is used to pass attributes to and from the Index itself.
291 // How it is initialized determines what action is taken when an Index object is instantiated with the IndexData.
292 // The choices are:
293 // a) Build an index for an las file
294 // 1) std::ostream *ofs must be supplied as well as std::istream *ifs or Reader *reader and a full file path
295 // for writing a temp file, const char *tmpfilenme.
296 // b) Examine an index for an las file
297 // 1) std::istream *ifs or Reader *reader must be supplied for the LAS file containing the point data
298 // 2) if the index to be read is in a standalone file then Reader *idxreader must also be supplied
299 // Options for building are
300 // a) build a new index even if an old one exists, overwriting the old one
301 // 1) forcenewindex must be true
302 // 2) std::ostream *ofs must be a valid ostream where there is storage space for the desired output
303 // b) only build an index if none exists
304 // 1) forcenewindex must be false
305 // 2) std::ostream *ofs must be a valid ostream where there is storage space for the desired output
306 // c) do not build a new index under any circumstances
307 // 1) readonly must be true
308 // Location of the index can be specified
309 // a) build the index within the las file VLR structure
310 // 1) writestandaloneindex must be false
311 // 2) std::ostream *ofs must be a valid ostream where there is storage space for a full copy
312 // of the LAS file plus the new index which is typically less than 5% of the original file size
313 // b) build a stand-alone index outside the las file
314 // 1) writestandaloneindex must be true
315 // 2) std::ostream *ofs must be a valid ostream where there is storage space for the new index
316 // which is typically less than 5% of the original file size
317 
318 // How the index is built is determined also by members of the IndexData class object.
319 // Options include:
320 // a) control the maximum memory used during the build process
321 // 1) pass a value for maxmem in bytes greater than 0. 0 resolves to default LIBLAS_INDEX_MAXMEMDEFAULT.
322 // b) debug messages generated during index creation or filtering. The higher the number, the more messages.
323 // 0) no debug reports
324 // 1) general info messages
325 // 2) status messages
326 // 3) cell statistics
327 // 4) progress status
328 // c) where debug messages are sent
329 // 1) default is stderr
330 // d) control the creation of z-dimensional cells and what z cell size to use
331 // 1) to turn on z-dimensional binning, use a value larger than 0 for zbinht
332 // e) data can be stored in index header for later use in recognizing the index.
333 // 1) Index author indexauthor - provided by author at time of creation
334 // 2) Index comment indexcomment - provided by author at time of creation
335 // 3) Index creation date indexdate - provided by author at time of creation
336 // The fields are not validated in any way by the index building code and are just three fields
337 // which can be used as the user sees fit. Maximum length is LIBLAS_INDEX_MAXSTRLEN - 1.
338 
339 // Once an index is built, or if an index already exists, the IndexData can be configured
340 // to define the bounds of a filter operation. Any dimension whose bounds pair are equal will
341 // be disregarded for the purpose of filtering. Filtering on the Z axis can still be performed even if the
342 // index was not built with Z cell sorting. Bounds must be defined in the same units and coordinate
343 // system that a liblas::Header returns with the commands GetMin{X|Y|Z} and a liblas::Point returns with
344 // Get{X|Y|Z}
345 
347 {
348 friend class Index;
349 friend class IndexIterator;
350 
351 public:
352  IndexData(void);
353  IndexData(Index const& index);
354 
355  // use one of these methods to configure the IndexData with the values needed for specific tasks
356 
357  // one comprehensive method to set all the values used in index initialization
358  bool SetInitialValues(std::istream *ifs = 0, Reader *reader = 0, std::ostream *ofs = 0, Reader *idxreader = 0,
359  const char *tmpfilenme = 0, const char *indexauthor = 0,
360  const char *indexcomment = 0, const char *indexdate = 0, double zbinht = 0.0,
361  uint32_t maxmem = LIBLAS_INDEX_MAXMEMDEFAULT, int debugoutputlevel = 0, bool readonly = 0,
362  bool writestandaloneindex = 0, bool forcenewindex = 0, FILE *debugger = 0);
363 
364  // set the values needed for building an index embedded in existing las file, overriding any existing index
365  bool SetBuildEmbedValues(Reader *reader, std::ostream *ofs, const char *tmpfilenme, const char *indexauthor = 0,
366  const char *indexcomment = 0, const char *indexdate = 0, double zbinht = 0.0,
367  uint32_t maxmem = LIBLAS_INDEX_MAXMEMDEFAULT, int debugoutputlevel = 0, FILE *debugger = 0);
368 
369  // set the values needed for building an index in a standalone file, overriding any existing index
370  bool SetBuildAloneValues(Reader *reader, std::ostream *ofs, const char *tmpfilenme, const char *indexauthor = 0,
371  const char *indexcomment = 0, const char *indexdate = 0, double zbinht = 0.0,
372  uint32_t maxmem = LIBLAS_INDEX_MAXMEMDEFAULT, int debugoutputlevel = 0, FILE *debugger = 0);
373 
374  // set the values needed for filtering with an existing index in an las file
375  bool SetReadEmbedValues(Reader *reader, int debugoutputlevel = 0, FILE *debugger = 0);
376 
377  // set the values needed for filtering with an existing index in a standalone file
378  bool SetReadAloneValues(Reader *reader, Reader *idxreader, int debugoutputlevel = 0, FILE *debugger = 0);
379 
380  // set the values needed for building an index embedded in existing las file only if no index already exists
381  // otherwise, prepare the existing index for filtering
382  bool SetReadOrBuildEmbedValues(Reader *reader, std::ostream *ofs, const char *tmpfilenme, const char *indexauthor = 0,
383  const char *indexcomment = 0, const char *indexdate = 0, double zbinht = 0.0,
384  uint32_t maxmem = LIBLAS_INDEX_MAXMEMDEFAULT, int debugoutputlevel = 0, FILE *debugger = 0);
385 
386  // set the values needed for building an index in a standalone file only if no index already exists in the las file
387  // otherwise, prepare the existing index for filtering
388  bool SetReadOrBuildAloneValues(Reader *reader, std::ostream *ofs, const char *tmpfilenme, const char *indexauthor = 0,
389  const char *indexcomment = 0, const char *indexdate = 0, double zbinht = 0.0,
390  uint32_t maxmem = LIBLAS_INDEX_MAXMEMDEFAULT, int debugoutputlevel = 0, FILE *debugger = 0);
391 
392  // set the bounds for use in filtering
393  bool SetFilterValues(double LowFilterX, double HighFilterX, double LowFilterY, double HighFilterY, double LowFilterZ, double HighFilterZ,
394  Index const& index);
395  bool SetFilterValues(Bounds<double> const& src, Index const& index);
396 
398  IndexData(IndexData const& other);
400  IndexData& operator=(IndexData const& rhs);
401 
402 private:
403  void SetValues(void);
404  bool CalcFilterEnablers(void);
405  void Copy(IndexData const& other);
406 
407 protected:
412  std::istream *m_ifs;
413  std::ostream *m_ofs;
414  const char *m_tempFileName;
415  const char *m_indexAuthor;
416  const char *m_indexComment;
417  const char *m_indexDate;
418  double m_cellSizeZ;
419  double m_LowXBorderPartCell, m_HighXBorderPartCell, m_LowYBorderPartCell, m_HighYBorderPartCell;
420  int32_t m_LowXCellCompletelyIn, m_HighXCellCompletelyIn, m_LowYCellCompletelyIn, m_HighYCellCompletelyIn,
421  m_LowZCellCompletelyIn, m_HighZCellCompletelyIn;
422  int32_t m_LowXBorderCell, m_HighXBorderCell, m_LowYBorderCell, m_HighYBorderCell,
423  m_LowZBorderCell, m_HighZBorderCell;
426  bool m_noFilterX, m_noFilterY, m_noFilterZ, m_readOnly, m_writestandaloneindex, m_forceNewIndex, m_indexValid;
427  FILE *m_debugger;
428 
429  void SetIterator(IndexIterator *setIt) {m_iterator = setIt;}
430  IndexIterator *GetIterator(void) {return(m_iterator);}
431 
432 public:
433  double GetCellSizeZ(void) const {return m_cellSizeZ;}
434  FILE *GetDebugger(void) const {return m_debugger;}
435  bool GetReadOnly(void) const {return m_readOnly;}
436  bool GetStandaloneIndex(void) const {return m_writestandaloneindex;}
437  bool GetForceNewIndex(void) const {return m_forceNewIndex;}
438  uint32_t GetMaxMemoryUsage(void) const {return m_maxMemoryUsage;}
439  Reader *GetReader(void) const {return m_reader;}
440  int GetDebugOutputLevel(void) const {return m_debugOutputLevel;}
441  const char *GetTempFileName(void) const {return m_tempFileName;}
442  const char *GetIndexAuthorStr(void) const;
443  const char *GetIndexCommentStr(void) const;
444  const char *GetIndexDateStr(void) const;
445  double GetMinFilterX(void) const {return (m_filter.min)(0);}
446  double GetMaxFilterX(void) const {return (m_filter.max)(0);}
447  double GetMinFilterY(void) const {return (m_filter.min)(1);}
448  double GetMaxFilterY(void) const {return (m_filter.max)(1);}
449  double GetMinFilterZ(void) const {return (m_filter.min)(2);}
450  double GetMaxFilterZ(void) const {return (m_filter.max)(2);}
451  void ClampFilterBounds(Bounds<double> const& m_bounds);
452  void SetReader(Reader *reader) {m_reader = reader;}
453  void SetIStream(std::istream *ifs) {m_ifs = ifs;}
454  void SetOStream(std::ostream *ofs) {m_ofs = ofs;}
455  void SetTmpFileName(const char *tmpfilenme) {m_tempFileName = tmpfilenme;}
456  void SetIndexAuthor(const char *indexauthor) {m_indexAuthor = indexauthor;}
457  void SetIndexComment(const char *indexcomment) {m_indexComment = indexcomment;}
458  void SetIndexDate(const char *indexdate) {m_indexDate = indexdate;}
459  void SetCellSizeZ(double cellsizez) {m_cellSizeZ = cellsizez;}
460  void SetMaxMem(uint32_t maxmem) {m_maxMemoryUsage = maxmem;}
461  void SetDebugOutputLevel(int debugoutputlevel) {m_debugOutputLevel = debugoutputlevel;}
462  void SetReadOnly(bool readonly) {m_readOnly = readonly;}
463  void SetStandaloneIndex(bool writestandaloneindex) {m_writestandaloneindex = writestandaloneindex;}
464  void SetDebugger(FILE *debugger) {m_debugger = debugger;}
465 };
466 
468 {
469 friend class Index;
470 
471 protected:
474  uint32_t m_chunkSize, m_advance;
475  uint32_t m_curVLR, m_curCellStartPos, m_curCellX, m_curCellY, m_totalPointsScanned, m_ptsScannedCurCell,
476  m_ptsScannedCurVLR;
478 
479 public:
480  IndexIterator(Index *IndexSrc, double LowFilterX, double HighFilterX, double LowFilterY, double HighFilterY,
481  double LowFilterZ, double HighFilterZ, uint32_t ChunkSize);
482  IndexIterator(Index *IndexSrc, IndexData const& IndexDataSrc, uint32_t ChunkSize);
483  IndexIterator(Index *IndexSrc, Bounds<double> const& BoundsSrc, uint32_t ChunkSize);
485  IndexIterator(IndexIterator const& other);
487  IndexIterator& operator=(IndexIterator const& rhs);
488 private:
489  void Copy(IndexIterator const& other);
490  void ResetPosition(void);
491  uint8_t MinMajorVersion(void) {return(1);}
492  uint8_t MinMinorVersion(void) {return(2);}
493 
494 public:
496  const std::vector<uint32_t>& advance(int32_t n);
498  const std::vector<uint32_t>& operator()(int32_t n);
500  inline const std::vector<uint32_t>& operator++() {return (advance(1));}
502  inline const std::vector<uint32_t>& operator++(int) {return (advance(1));}
504  inline const std::vector<uint32_t>& operator--() {return (advance(-1));}
506  inline const std::vector<uint32_t>& operator--(int) {return (advance(-1));}
508  inline const std::vector<uint32_t>& operator+=(int32_t n) {return (advance(n));}
510  inline const std::vector<uint32_t>& operator+(int32_t n) {return (advance(n));}
512  inline const std::vector<uint32_t>& operator-=(int32_t n) {return (advance(-n));}
514  inline const std::vector<uint32_t>& operator-(int32_t n) {return (advance(-n));}
516  inline const std::vector<uint32_t>& operator[](int32_t n) {return ((*this)(n));}
518  bool ValidateIndexVersion(uint8_t VersionMajor, uint8_t VersionMinor) {return (VersionMajor > MinMajorVersion() || (VersionMajor == MinMajorVersion() && VersionMinor >= MinMinorVersion()));}
519 };
520 
521 template <typename T, typename Q>
522 inline void ReadVLRData_n(T& dest, IndexVLRData const& src, Q& pos)
523 {
524  // error if reading past array end
525  if (static_cast<size_t>(pos) + sizeof(T) > src.size())
526  throw std::out_of_range("liblas::detail::ReadVLRData_n: array index out of range");
527  // copy sizeof(T) bytes to destination
528  memcpy(&dest, &src[pos], sizeof(T));
529  // Fix little-endian
530  LIBLAS_SWAP_BYTES_N(dest, sizeof(T));
531  // increment the write position to end of written data
532  pos = pos + static_cast<Q>(sizeof(T));
533 }
534 
535 template <typename T, typename Q>
536 inline void ReadVLRDataNoInc_n(T& dest, IndexVLRData const& src, Q const& pos)
537 {
538  // error if reading past array end
539  if (static_cast<size_t>(pos) + sizeof(T) > src.size())
540  throw std::out_of_range("liblas::detail::ReadVLRDataNoInc_n: array index out of range");
541  // copy sizeof(T) bytes to destination
542  memcpy(&dest, &src[pos], sizeof(T));
543  // Fix little-endian
544  LIBLAS_SWAP_BYTES_N(dest, sizeof(T));
545 }
546 
547 template <typename T, typename Q>
548 inline void ReadeVLRData_str(char * dest, IndexVLRData const& src, T const srclen, Q& pos)
549 {
550  // error if reading past array end
551  if (static_cast<size_t>(pos) + static_cast<size_t>(srclen) > src.size())
552  throw std::out_of_range("liblas::detail::ReadeVLRData_str: array index out of range");
553  // copy srclen bytes to destination
554  memcpy(dest, &src[pos], srclen);
555  // increment the write position to end of written data
556  pos = pos + static_cast<Q>(srclen);
557 }
558 
559 template <typename T, typename Q>
560 inline void ReadVLRDataNoInc_str(char * dest, IndexVLRData const& src, T const srclen, Q pos)
561 {
562  // error if reading past array end
563  if (static_cast<size_t>(pos) + static_cast<size_t>(srclen) > src.size())
564  throw std::out_of_range("liblas::detail::ReadVLRDataNoInc_str: array index out of range");
565  // copy srclen bytes to destination
566  std::memcpy(dest, &src[pos], srclen);
567 }
568 
569 } // namespace liblas
570 
571 #endif // LIBLAS_LASINDEX_HPP_INCLUDED
bool GetForceNewIndex(void) const
Definition: index.hpp:437
IndexData m_indexData
Definition: index.hpp:472
void SetIndexAuthorStr(const char *ias)
Definition: index.hpp:274
void ReadVLRData_n(T &dest, IndexVLRData const &src, Q &pos)
Definition: index.hpp:522
void ReadVLRDataNoInc_n(T &dest, IndexVLRData const &src, Q const &pos)
Definition: index.hpp:536
void SetDebugOutputLevel(int debugoutputlevel)
Definition: index.hpp:461
bool GetStandaloneIndex(void) const
Definition: index.hpp:436
Reader * m_idxreader
Definition: index.hpp:409
const std::vector< uint32_t > & operator-=(int32_t n)
returns set of filter-compliant points beginning n points backwards from the end of the last set...
Definition: index.hpp:512
uint32_t GetCellsY(void) const
Definition: index.hpp:244
uint32_t GetCellsX(void) const
Definition: index.hpp:243
Representation of variable-length record data.
Definition: variablerecord.hpp:59
IndexIterator * GetIterator(void)
Definition: index.hpp:430
#define LAS_DLL
Definition: export.hpp:58
double GetRangeX(void) const
Definition: index.hpp:236
Reader * GetReader(void) const
Definition: index.hpp:439
const std::vector< uint32_t > & operator++()
returns next set of filter-compliant points with no skipped points
Definition: index.hpp:500
void SetIndexCommentStr(const char *ics)
Definition: index.hpp:275
const std::vector< uint32_t > & operator[](int32_t n)
returns filter-compliant points as though the first point returned is element n in a zero-based array...
Definition: index.hpp:516
FILE * m_debugger
Definition: index.hpp:427
double GetMaxFilterY(void) const
Definition: index.hpp:448
uint8_t GetVersionMinor(void) const
Definition: index.hpp:270
class LAS_DLL IndexIterator
Definition: index.hpp:80
void SetCellsX(uint32_t cellsX)
Definition: index.hpp:284
double m_LowYBorderPartCell
Definition: index.hpp:419
const std::vector< uint32_t > & operator++(int)
returns next set of filter-compliant points with no skipped points
Definition: index.hpp:502
bool GetStandaloneIndex(void) const
Definition: index.hpp:255
std::istream * m_ifs
Definition: index.hpp:412
Bounds< double > m_filter
Definition: index.hpp:411
void SetDebugger(FILE *debugger)
Definition: index.hpp:464
int32_t m_LowZBorderCell
Definition: index.hpp:422
void SetReader(Reader *reader)
Definition: index.hpp:452
FILE * GetDebugger(void) const
Definition: index.hpp:253
Index * m_index
Definition: index.hpp:473
bool GetForceNewIndex(void) const
Definition: index.hpp:256
double GetMaxY(void) const
Definition: index.hpp:232
Reader * GetIndexReader(void) const
Definition: index.hpp:263
int GetDebugOutputLevel(void) const
Definition: index.hpp:440
bool m_writestandaloneindex
Definition: index.hpp:426
double GetMinZ(void) const
Definition: index.hpp:233
void SetMinX(double minX)
Definition: index.hpp:277
double GetMaxFilterX(void) const
Definition: index.hpp:446
void SetMaxY(double maxY)
Definition: index.hpp:280
const char * m_tempFileName
Definition: index.hpp:414
const char * m_indexComment
Definition: index.hpp:416
const std::vector< uint32_t > & operator+=(int32_t n)
returns next set of filter-compliant points with n-1 skipped points, for n<0 acts like -=() ...
Definition: index.hpp:508
void SetOStream(std::ostream *ofs)
Definition: index.hpp:454
double GetMinFilterZ(void) const
Definition: index.hpp:449
void SetStandaloneIndex(bool writestandaloneindex)
Definition: index.hpp:463
uint32_t m_maxMemoryUsage
Definition: index.hpp:424
Definition: index.hpp:346
class LAS_DLL IndexData
Definition: index.hpp:79
IndexIterator * m_iterator
Definition: index.hpp:410
double GetMaxX(void) const
Definition: index.hpp:230
const char * GetTempFileName(void) const
Definition: index.hpp:441
void SetCellsY(uint32_t cellsY)
Definition: index.hpp:285
FILE * GetDebugger(void) const
Definition: index.hpp:434
void SetIndexComment(const char *indexcomment)
Definition: index.hpp:457
std::vector< IndexCellRow > IndexCellDataBlock
Definition: index.hpp:77
uint32_t GetCellsZ(void) const
Definition: index.hpp:246
const char * m_indexDate
Definition: index.hpp:417
Header * GetIndexHeader(void)
Definition: index.hpp:261
void SetPointRecordsCount(uint32_t prc)
Definition: index.hpp:283
void SetIterator(IndexIterator *setIt)
Definition: index.hpp:429
void SetIndexDateStr(const char *ids)
Definition: index.hpp:276
std::vector< liblas::detail::IndexCell > IndexCellRow
Definition: index.hpp:76
void SetCellsZ(uint32_t cellsZ)
Definition: index.hpp:286
Definition: index.hpp:467
const char * m_indexAuthor
Definition: index.hpp:415
bool IndexFailed(void) const
Definition: index.hpp:217
Bounds< double > const & GetBounds(void) const
Definition: index.hpp:239
Defines public interface to LAS reader implementation.
Definition: reader.hpp:66
uint32_t GetMaxMemoryUsage(void) const
Definition: index.hpp:438
Definition: index.hpp:119
double GetCellSizeZ(void) const
Definition: index.hpp:251
int32_t m_LowZCellCompletelyIn
Definition: index.hpp:420
void SetIndexAuthor(const char *indexauthor)
Definition: index.hpp:456
void SetMaxZ(double maxZ)
Definition: index.hpp:282
bool IndexReady(void) const
Definition: index.hpp:218
Header * GetPointHeader(void)
Definition: index.hpp:260
uint32_t m_conformingPtsFound
Definition: index.hpp:477
std::vector< uint8_t > IndexVLRData
Definition: index.hpp:75
int GetDebugOutputLevel(void) const
Definition: index.hpp:258
void SetMaxMem(uint32_t maxmem)
Definition: index.hpp:460
Reader * m_reader
Definition: index.hpp:408
double m_cellSizeZ
Definition: index.hpp:418
void SetMaxX(double maxX)
Definition: index.hpp:278
Namespace grouping all elements of libLAS public interface.
Definition: bounds.hpp:60
Reader * GetReader(void) const
Definition: index.hpp:262
T() max(std::size_t const &index) const
Definition: bounds.hpp:307
void SetMinZ(double minZ)
Definition: index.hpp:281
int m_debugOutputLevel
Definition: index.hpp:425
void SetTmpFileName(const char *tmpfilenme)
Definition: index.hpp:455
T() min(std::size_t const &index) const
Definition: bounds.hpp:287
void ReadeVLRData_str(char *dest, IndexVLRData const &src, T const srclen, Q &pos)
Definition: index.hpp:548
const char * GetTempFileName(void) const
Definition: index.hpp:264
double GetMaxFilterZ(void) const
Definition: index.hpp:450
Point data record composed with X, Y, Z coordinates and attributes.
Definition: point.hpp:68
const std::vector< uint32_t > & operator--(int)
returns set of filter-compliant points skipping backwards 1 from the end of the last set ...
Definition: index.hpp:506
bool GetReadOnly(void) const
Definition: index.hpp:254
uint32_t GetDataVLR_ID(void) const
Definition: index.hpp:249
const std::vector< uint32_t > & operator+(int32_t n)
returns next set of filter-compliant points with n-1 skipped points, for n<0 acts like -() ...
Definition: index.hpp:510
void ReadVLRDataNoInc_str(char *dest, IndexVLRData const &src, T const srclen, Q pos)
Definition: index.hpp:560
const std::vector< uint32_t > & operator-(int32_t n)
returns set of filter-compliant points beginning n points backwards from the end of the last set...
Definition: index.hpp:514
const std::vector< uint32_t > & operator--()
returns set of filter-compliant points skipping backwards 1 from the end of the last set ...
Definition: index.hpp:504
std::ostream * m_ofs
Definition: index.hpp:413
uint32_t GetMaxMemoryUsage(void) const
Definition: index.hpp:257
void SetReadOnly(bool readonly)
Definition: index.hpp:462
void SetIndexDate(const char *indexdate)
Definition: index.hpp:458
void SetDataVLR_ID(uint32_t DataVLR_ID)
Definition: index.hpp:273
double GetMinX(void) const
Definition: index.hpp:229
void SetMinY(double minY)
Definition: index.hpp:279
double GetMinFilterY(void) const
Definition: index.hpp:447
double GetMinY(void) const
Definition: index.hpp:231
uint32_t m_totalPointsScanned
Definition: index.hpp:475
uint32_t GetPointRecordsCount(void) const
Definition: index.hpp:241
void SetCellSizeZ(double cellsizez)
Definition: index.hpp:459
double GetRangeY(void) const
Definition: index.hpp:237
bool GetReadOnly(void) const
Definition: index.hpp:435
uint32_t m_chunkSize
Definition: index.hpp:474
Definition: schema.hpp:80
#define LIBLAS_INDEX_MAXMEMDEFAULT
Definition: index.hpp:61
bool ValidateIndexVersion(uint8_t VersionMajor, uint8_t VersionMinor)
tests viability of index for filtering with iterator
Definition: index.hpp:518
double GetRangeZ(void) const
Definition: index.hpp:238
double GetMinFilterX(void) const
Definition: index.hpp:445
double GetCellSizeZ(void) const
Definition: index.hpp:433
Definition of public header block.
Definition: header.hpp:78
void SetIStream(std::istream *ifs)
Definition: index.hpp:453
double GetMaxZ(void) const
Definition: index.hpp:234
uint8_t GetVersionMajor(void) const
Definition: index.hpp:269