Visual Computing Library
Loading...
Searching...
No Matches
pointer_container_component.h
1/*****************************************************************************
2 * VCLib *
3 * Visual Computing Library *
4 * *
5 * Copyright(C) 2021-2025 *
6 * Visual Computing Lab *
7 * ISTI - Italian National Research Council *
8 * *
9 * All rights reserved. *
10 * *
11 * This program is free software; you can redistribute it and/or modify *
12 * it under the terms of the Mozilla Public License Version 2.0 as published *
13 * by the Mozilla Foundation; either version 2 of the License, or *
14 * (at your option) any later version. *
15 * *
16 * This program is distributed in the hope that it will be useful, *
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
19 * Mozilla Public License Version 2.0 *
20 * (https://www.mozilla.org/en-US/MPL/2.0/) for more details. *
21 ****************************************************************************/
22
23#ifndef VCL_MESH_COMPONENTS_BASES_POINTER_CONTAINER_COMPONENT_H
24#define VCL_MESH_COMPONENTS_BASES_POINTER_CONTAINER_COMPONENT_H
25
26#include "container_component.h"
27
28#include <vclib/mesh/iterators/components/index_from_pointer_iterator.h>
29#include <vclib/misc/iterators/const_pointer_iterator.h>
30
31namespace vcl::comp {
32
74template<
75 typename DerivedComponent, // CRTP pattern, derived class
76 uint COMP_ID, // component id
77 typename Elem, // element type for which the pointers are stored
78 int N, // container size
79 typename ParentElemType, // parent element type
80 bool VERT, // true if component vertical
81 bool OPT, // true if component vertical and optional
82 bool TTVN> // true if container size tied to vertex number
84 public ContainerComponent<
85 DerivedComponent,
86 COMP_ID,
87 Elem*,
88 N,
89 void,
90 ParentElemType,
91 VERT,
92 OPT,
93 TTVN,
94 Elem>
95{
98 COMP_ID,
99 Elem*,
100 N,
101 void,
103 VERT,
104 OPT,
105 TTVN,
106 Elem>;
107
108public:
117 template<typename T>
119 {
120 return View(
121 ConstIterator(Base::container().begin()),
122 ConstIterator(Base::container().end()));
123 }
124
125protected:
126 using Base::container;
127
128 using Iterator = Base::ConstIterator;
130 using ConstIndexIterator = IndexFromPointerIterator<ConstIterator>;
131
132 /*
133 * This member function is called when we need to update the pointers in
134 * this container after a reallocation (the pointer of the first element of
135 * the container of Elem is changed).
136 *
137 * This is necessary when, for example, the original container of Elements
138 * has been reallocated. When this happens, the all the Elements have been
139 * moved in another portion of memory, and all the pointers to that Elements
140 * must be updated. Since in this container are stored pointers to Elements,
141 * we need to update them.
142 *
143 * To update them, we need to know the oldBase (the pointer to the first
144 * Element of the reallocated Container before the reallocation). We can
145 * then compute, for each pointer, the difference w.r.t. the old address of
146 * the first element of the Container, and update the the pointer
147 * accordingly using the new base of the Container, which is computed
148 * trough the parent mesh.
149 *
150 * When we perform an append operation, we need to update the pointers
151 * taking into account also the offset: when we append a new element in a
152 * container, only its pointers must be updated. To update from the old
153 * pointers to the new ones, we need to know how many elements were in the
154 * container BEFORE the append operation, and this becomes the offset to
155 * be applied to the pointers of the newly appended elements.
156 */
157 void updateReferences(const Elem* oldBase, std::size_t offset = 0)
158 {
159 const Elem* newBase = baseOfElemContainer();
160
161 auto& baseContainer = Base::container();
162
163 for (uint j = 0; j < baseContainer.size();
164 ++j) { // for each pointer in this container
165 if (baseContainer.at(j) != nullptr) {
166 size_t diff =
167 baseContainer.at(j) - oldBase; // offset w.r.t. the old base
168
169 // update the pointer using newBase
170 baseContainer.at(j) = (Elem*) newBase + diff + offset;
171 }
172 }
173 }
174
175 /*
176 * This member function is called when we need to update the pointers in
177 * this containers, usually after a compaction of the container (but not
178 * always).
179 *
180 * In this case, the address of the first element in the container is not
181 * changed, but may change the position of each element inside the
182 * container. The function takes the base pointer of the first element of
183 * the container, and a vector that stores, for each old element position,
184 * the new position in the container (UINT_NULL if the element has been
185 * removed and must be left unreferenced).
186 */
187 void updateReferences(const std::vector<uint>& newIndices)
188 {
189 const Elem* base = baseOfElemContainer();
190
191 auto& baseContainer = Base::container();
192
193 for (uint j = 0; j < baseContainer.size(); ++j) {
194 if (baseContainer.at(j) != nullptr) {
195 size_t diff = baseContainer.at(j) - base;
196 if (newIndices[diff] == UINT_NULL) { // element has been removed
197 baseContainer.at(j) = nullptr;
198 }
199 else { // the new pointer will be base + newIndices[diff]
200 baseContainer.at(j) = (Elem*) base + newIndices[diff];
201 }
202 }
203 }
204 }
205
206private:
207 const Elem* baseOfElemContainer() const
208 {
209 return &(Base::parentElement()
210 ->parentMesh()
211 ->template element<Elem::ELEMENT_ID>(0));
212 }
213};
214
215} // namespace vcl::comp
216
217#endif // VCL_MESH_COMPONENTS_BASES_POINTER_CONTAINER_COMPONENT_H
A class representing a line segment in n-dimensional space. The class is parameterized by a PointConc...
Definition segment.h:43
The View class is a simple class that stores and exposes two iterators begin and end.
Definition view.h:67
The ContainerComponent class is the base class for all the components of VCLib that store a container...
Definition container_component.h:130
The PointerContainerComponent is the base class for all the components of VCLib that store a containe...
Definition pointer_container_component.h:95
auto pointers() const
Exposes the pointers in the container as a View.
Definition pointer_container_component.h:118
constexpr uint UINT_NULL
The UINT_NULL value represent a null value of uint that is the maximum value that can be represented ...
Definition base.h:48