Nektar++
Octree.h
Go to the documentation of this file.
1 ///////////////////////////////////////////////////////////////////////////////
2 //
3 // File: Octree.h
4 //
5 // For more information, please see: http://www.nektar.info
6 //
7 // The MIT License
8 //
9 // Copyright (c) 2006 Division of Applied Mathematics, Brown University (USA),
10 // Department of Aeronautics, Imperial College London (UK), and Scientific
11 // Computing and Imaging Institute, University of Utah (USA).
12 //
13 // Permission is hereby granted, free of charge, to any person obtaining a
14 // copy of this software and associated documentation files (the "Software"),
15 // to deal in the Software without restriction, including without limitation
16 // the rights to use, copy, modify, merge, publish, distribute, sublicense,
17 // and/or sell copies of the Software, and to permit persons to whom the
18 // Software is furnished to do so, subject to the following conditions:
19 //
20 // The above copyright notice and this permission notice shall be included
21 // in all copies or substantial portions of the Software.
22 //
23 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
24 // OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
25 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
26 // THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
27 // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
28 // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
29 // DEALINGS IN THE SOFTWARE.
30 //
31 // Description: Octree header.
32 //
33 ///////////////////////////////////////////////////////////////////////////////
34 
36 #include <limits>
37 #include <memory>
38 #include <vector>
39 
40 namespace Nektar
41 {
42 namespace FieldUtils
43 {
44 
45 class Octree
46 {
47  class Octant;
48  using OctantSharedPtr = std::shared_ptr<Octant>;
49  using OctantWeakPtr = std::weak_ptr<Octant>;
50 
51 public:
52  // Empty constructor
53  Octree();
54  // Constructor with bounds
55  Octree(const Array<OneD, Array<OneD, NekDouble>> &pts, int maxPts,
56  const Array<OneD, NekDouble> &bounds);
57  // Constructor without bounds
58  Octree(const Array<OneD, Array<OneD, NekDouble>> &pts, int maxPts);
59 
60  // Returns the ID of the leaf node that contains 'coords'
61  int QueryNode(const Array<OneD, NekDouble> &coords,
62  int depth = std::numeric_limits<int>::max());
63  // Returns the ID of the point in 'pts' closest to 'coords'
65  const Array<OneD, NekDouble> &coords, double &distance,
66  int pointInd = -1);
67 
68  // Returns the ID of the points inside the node 'nodeID'
69  std::vector<int> QueryPoints(int nodeID);
70  // Returns the IDs of the leaf nodes neighbouring 'nodeID'
71  std::vector<int> QueryNeighbours(int nodeID);
72 
73  int QueryNpoints(int nodeID)
74  {
75  return m_nodes[nodeID]->GetNpoints();
76  }
77  int QueryLocation(int nodeID)
78  {
79  return m_nodes[nodeID]->GetLoc();
80  }
81  int QueryDepth(int nodeID)
82  {
83  return m_nodes[nodeID]->GetDepth();
84  }
85  int QueryDelta(int nodeID)
86  {
87  return m_nodes[nodeID]->GetDelta();
88  }
89 
90  // Get some statistics about the octree
91  void GetStats(int &maxPts, int &nPts, int &nNodes, int &nLeaves,
92  int &depth);
93 
94 private:
95  class Octant : public std::enable_shared_from_this<Octant>
96  {
97  public:
98  // Empty constructor
99  Octant();
100  // Constructor
101  Octant(int loc, int depth, int id,
102  const Array<OneD, NekDouble> &bounds);
103  // Copy constructor
104  Octant(int loc, Octant &parent);
105 
106  int GetNpoints() const
107  {
108  return m_nPts;
109  }
110  int GetLoc() const
111  {
112  return m_loc;
113  }
114  int GetDepth() const
115  {
116  return m_depth;
117  }
118  double GetDelta() const
119  {
120  return m_delta;
121  }
122  int GetID() const
123  {
124  return m_id;
125  }
126  bool IsLeaf() const
127  {
128  return m_isLeaf;
129  }
131  {
132  return m_centre;
133  }
135  {
136  return m_bounds;
137  }
138  std::vector<int> &GetIndices()
139  {
140  return m_pointInd;
141  }
143  {
144  return m_children;
145  }
146  std::vector<OctantWeakPtr> &GetNeighbours()
147  {
148  return m_neighbours;
149  }
150 
151  void SetID(int id)
152  {
153  m_id = id;
154  }
155 
156  void GetLeaves(std::vector<OctantSharedPtr> &leaves);
157  void SetIndices(const std::vector<int> &indices);
158  void AddNeighbours(const std::vector<OctantSharedPtr> &neighbours);
159  void AddPoints(const Array<OneD, Array<OneD, NekDouble>> &pts,
160  const std::vector<int> &indices);
161  void Subdivide(int maxPts,
162  const Array<OneD, Array<OneD, NekDouble>> &pts,
163  std::vector<OctantSharedPtr> &nodes);
164  int GetLocInNode(const Array<OneD, NekDouble> &coords);
165 
166  private:
167  /// Number of points in the octant
168  int m_nPts;
169  /// Position in the father octant (1-8)
170  int m_loc;
171  /// Depth in octree (root is 1)
172  int m_depth;
173  /// ID of the octant (index in 'm_nodes' vector)
174  int m_id;
175  /// Length of the octant side
176  double m_delta;
177  /// Coordinates of the centre of the octant
179  /// Min/max coordinates of the octant (x, y, z)
181  /// Indices of the points comprised by the octant
182  std::vector<int> m_pointInd;
183  /// True for a leaf octant, false otherwise
184  bool m_isLeaf;
185 
186  /// Vector of pointers to the children octants
188  /// Vector of pointers to the neighbouring octants
189  std::vector<OctantWeakPtr> m_neighbours;
190  };
191 
192  /// Max points allowed in each octant
193  int m_maxPts;
194  /// Number of points in the mesh
196  /// Number of octants in the tree
197  int m_nNodes;
198  /// Number of leaf nodes in the tree
200  /// Maximum depth of the tree
202 
203  /// First node of the tree, linked to the rest
205  /// Vector of pointers to every octant in the tree
206  std::vector<OctantSharedPtr> m_nodes;
207 
208  void AdvanceToStats(int nodeID);
209  void SetNeighbours(int nodeID);
210 };
211 } // namespace FieldUtils
212 } // namespace Nektar
Array< OneD, NekDouble > m_centre
Coordinates of the centre of the octant.
Definition: Octree.h:178
int m_depth
Depth in octree (root is 1)
Definition: Octree.h:172
Array< OneD, NekDouble > & GetBounds()
Definition: Octree.h:134
double m_delta
Length of the octant side.
Definition: Octree.h:176
std::vector< OctantWeakPtr > & GetNeighbours()
Definition: Octree.h:146
void AddNeighbours(const std::vector< OctantSharedPtr > &neighbours)
Adds to 'm_neighbours' the octants that are not already in the list.
Definition: Octree.cpp:528
void Subdivide(int maxPts, const Array< OneD, Array< OneD, NekDouble >> &pts, std::vector< OctantSharedPtr > &nodes)
Recursively divides the octant into 8 children and fills the leaf nodes with their corresponding poin...
Definition: Octree.cpp:593
int m_loc
Position in the father octant (1-8)
Definition: Octree.h:170
void GetLeaves(std::vector< OctantSharedPtr > &leaves)
Updates 'leaves' so that it contains all the leaf nodes belonging to the octant.
Definition: Octree.cpp:494
void SetIndices(const std::vector< int > &indices)
Sets the values of 'm_pointInd' to those in 'indices'.
Definition: Octree.cpp:514
std::vector< int > m_pointInd
Indices of the points comprised by the octant.
Definition: Octree.h:182
std::vector< OctantWeakPtr > m_neighbours
Vector of pointers to the neighbouring octants.
Definition: Octree.h:189
int m_nPts
Number of points in the octant.
Definition: Octree.h:168
Array< OneD, NekDouble > m_bounds
Min/max coordinates of the octant (x, y, z)
Definition: Octree.h:180
bool m_isLeaf
True for a leaf octant, false otherwise.
Definition: Octree.h:184
Array< OneD, OctantSharedPtr > & GetChildren()
Definition: Octree.h:142
std::vector< int > & GetIndices()
Definition: Octree.h:138
Array< OneD, NekDouble > & GetCentre()
Definition: Octree.h:130
int GetLocInNode(const Array< OneD, NekDouble > &coords)
Returns the position inside an octant in the range (1-8). The name convention is as follows: let be ...
Definition: Octree.cpp:636
void AddPoints(const Array< OneD, Array< OneD, NekDouble >> &pts, const std::vector< int > &indices)
Adds to 'm_pointInd' the IDs of the points in 'pts' that fall inside the octant.
Definition: Octree.cpp:556
int m_id
ID of the octant (index in 'm_nodes' vector)
Definition: Octree.h:174
Array< OneD, OctantSharedPtr > m_children
Vector of pointers to the children octants.
Definition: Octree.h:187
Octant()
Construct a new Octree::Octant object.
Definition: Octree.cpp:360
void SetNeighbours(int nodeID)
Once the nodes of the octree are created, sets their neighbours as explained in 'Octree::QueryNeighbo...
Definition: Octree.cpp:314
int QueryDepth(int nodeID)
Definition: Octree.h:81
OctantSharedPtr m_root
First node of the tree, linked to the rest.
Definition: Octree.h:204
std::vector< int > QueryNeighbours(int nodeID)
Returns the IDs of the octants that surround the queried node. First, it finds the neighbouring nodes...
Definition: Octree.cpp:252
std::vector< int > QueryPoints(int nodeID)
Returns the indices of the points of the mesh contained in the tree.
Definition: Octree.cpp:237
int QueryClosest(const Array< OneD, Array< OneD, NekDouble >> &pts, const Array< OneD, NekDouble > &coords, double &distance, int pointInd=-1)
Finds the ID of the closest point in 'pts' to the one specified by 'coords'. It also returns the dist...
Definition: Octree.cpp:178
int m_nNodes
Number of octants in the tree.
Definition: Octree.h:197
void GetStats(int &maxPts, int &nPts, int &nNodes, int &nLeaves, int &depth)
Returns some characteristic values of the tree.
Definition: Octree.cpp:271
int m_nLeaves
Number of leaf nodes in the tree.
Definition: Octree.h:199
std::shared_ptr< Octant > OctantSharedPtr
Definition: Octree.h:48
std::weak_ptr< Octant > OctantWeakPtr
Definition: Octree.h:49
int m_maxPts
Max points allowed in each octant.
Definition: Octree.h:193
int m_maxDepth
Maximum depth of the tree.
Definition: Octree.h:201
int QueryDelta(int nodeID)
Definition: Octree.h:85
int QueryLocation(int nodeID)
Definition: Octree.h:77
void AdvanceToStats(int nodeID)
Goes through all the nodes of the octree counting the number of octants and the maximum depth reached...
Definition: Octree.cpp:287
int QueryNpoints(int nodeID)
Definition: Octree.h:73
Octree()
Construct a new octree object.
Definition: Octree.cpp:48
int m_nMshPts
Number of points in the mesh.
Definition: Octree.h:195
std::vector< OctantSharedPtr > m_nodes
Vector of pointers to every octant in the tree.
Definition: Octree.h:206
int QueryNode(const Array< OneD, NekDouble > &coords, int depth=std::numeric_limits< int >::max())
Given the coordinates 'coords' of a point, returns the leaf octant that contains it....
Definition: Octree.cpp:139
The above copyright notice and this permission notice shall be included.
Definition: CoupledSolver.h:2