OpenMD 3.2
Molecular Dynamics in the Open
Loading...
Searching...
No Matches
DataStorage.cpp
Go to the documentation of this file.
1/*
2 * Copyright (c) 2004-present, The University of Notre Dame. All rights
3 * reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 *
8 * 1. Redistributions of source code must retain the above copyright notice,
9 * this list of conditions and the following disclaimer.
10 *
11 * 2. Redistributions in binary form must reproduce the above copyright notice,
12 * this list of conditions and the following disclaimer in the documentation
13 * and/or other materials provided with the distribution.
14 *
15 * 3. Neither the name of the copyright holder nor the names of its
16 * contributors may be used to endorse or promote products derived from
17 * this software without specific prior written permission.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
23 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE.
30 *
31 * SUPPORT OPEN SCIENCE! If you use OpenMD or its source code in your
32 * research, please cite the following paper when you publish your work:
33 *
34 * [1] Drisko et al., J. Open Source Softw. 9, 7004 (2024).
35 *
36 * Good starting points for code and simulation methodology are:
37 *
38 * [2] Meineke, et al., J. Comp. Chem. 26, 252-271 (2005).
39 * [3] Fennell & Gezelter, J. Chem. Phys. 124, 234104 (2006).
40 * [4] Sun, Lin & Gezelter, J. Chem. Phys. 128, 234107 (2008).
41 * [5] Vardeman, Stocker & Gezelter, J. Chem. Theory Comput. 7, 834 (2011).
42 * [6] Kuang & Gezelter, Mol. Phys., 110, 691-701 (2012).
43 * [7] Lamichhane, Gezelter & Newman, J. Chem. Phys. 141, 134109 (2014).
44 * [8] Bhattarai, Newman & Gezelter, Phys. Rev. B 99, 094106 (2019).
45 * [9] Drisko & Gezelter, J. Chem. Theory Comput. 20, 4986-4997 (2024).
46 */
47
48/**
49 * @file DataStorage.cpp
50 * @author tlin
51 * @date 10/26/2004
52 * @version 1.0
53 */
54
55#include "brains/DataStorage.hpp"
56using namespace std;
57namespace OpenMD {
58
59 DataStorage::DataStorage() : size_(0), storageLayout_(0) {}
60
61 DataStorage::DataStorage(std::size_t size, int storageLayout) : size_(size) {
62 setStorageLayout(storageLayout);
63 resize(size);
64 }
65
66 std::size_t DataStorage::getSize() {
67 if (storageLayout_ & dslPosition && position.size() != size_) {
68 // error
69 cerr << "size does not match" << endl;
70 }
71
72 if (storageLayout_ & dslVelocity && velocity.size() != size_) {
73 // error
74 cerr << "size does not match" << endl;
75 }
76
77 if (storageLayout_ & dslForce && force.size() != size_) {
78 // error
79 cerr << "size does not match" << endl;
80 }
81
82 if (storageLayout_ & dslAmat && aMat.size() != size_) {
83 // error
84 cerr << "size does not match" << endl;
85 }
86
87 if (storageLayout_ & dslAngularMomentum &&
88 angularMomentum.size() != size_) {
89 // error
90 cerr << "size does not match" << endl;
91 }
92
93 if (storageLayout_ & dslTorque && torque.size() != size_) {
94 // error
95 cerr << "size does not match" << endl;
96 }
97
98 if (storageLayout_ & dslParticlePot && particlePot.size() != size_) {
99 // error
100 cerr << "size does not match" << endl;
101 }
102
103 if (storageLayout_ & dslDensity && density.size() != size_) {
104 // error
105 cerr << "size does not match" << endl;
106 }
107
108 if (storageLayout_ & dslFunctional && functional.size() != size_) {
109 // error
110 cerr << "size does not match" << endl;
111 }
112
113 if (storageLayout_ & dslFunctionalDerivative &&
114 functionalDerivative.size() != size_) {
115 // error
116 cerr << "size does not match" << endl;
117 }
118
119 if (storageLayout_ & dslDipole && dipole.size() != size_) {
120 // error
121 cerr << "size does not match" << endl;
122 }
123
124 if (storageLayout_ & dslQuadrupole && quadrupole.size() != size_) {
125 // error
126 cerr << "size does not match" << endl;
127 }
128
129 if (storageLayout_ & dslElectricField && electricField.size() != size_) {
130 // error
131 cerr << "size does not match" << endl;
132 }
133
134 if (storageLayout_ & dslSkippedCharge && skippedCharge.size() != size_) {
135 // error
136 cerr << "size does not match" << endl;
137 }
138
139 if (storageLayout_ & dslFlucQPosition && flucQPos.size() != size_) {
140 // error
141 cerr << "size does not match" << endl;
142 }
143
144 if (storageLayout_ & dslFlucQVelocity && flucQVel.size() != size_) {
145 // error
146 cerr << "size does not match" << endl;
147 }
148
149 if (storageLayout_ & dslFlucQForce && flucQFrc.size() != size_) {
150 // error
151 cerr << "size does not match" << endl;
152 }
153
154 if (storageLayout_ & dslSitePotential && sitePotential.size() != size_) {
155 // error
156 cerr << "size does not match" << endl;
157 }
158
159 return size_;
160 }
161
162 void DataStorage::resize(std::size_t newSize) {
163 if (storageLayout_ & dslPosition) { internalResize(position, newSize); }
164
165 if (storageLayout_ & dslVelocity) { internalResize(velocity, newSize); }
166
167 if (storageLayout_ & dslForce) { internalResize(force, newSize); }
168
169 if (storageLayout_ & dslAmat) { internalResize(aMat, newSize); }
170
171 if (storageLayout_ & dslAngularMomentum) {
172 internalResize(angularMomentum, newSize);
173 }
174
175 if (storageLayout_ & dslTorque) { internalResize(torque, newSize); }
176
177 if (storageLayout_ & dslParticlePot) {
178 internalResize(particlePot, newSize);
179 }
180
181 if (storageLayout_ & dslDensity) { internalResize(density, newSize); }
182
183 if (storageLayout_ & dslFunctional) { internalResize(functional, newSize); }
184
185 if (storageLayout_ & dslFunctionalDerivative) {
186 internalResize(functionalDerivative, newSize);
187 }
188
189 if (storageLayout_ & dslDipole) { internalResize(dipole, newSize); }
190
191 if (storageLayout_ & dslQuadrupole) { internalResize(quadrupole, newSize); }
192
193 if (storageLayout_ & dslElectricField) {
194 internalResize(electricField, newSize);
195 }
196
197 if (storageLayout_ & dslSkippedCharge) {
198 internalResize(skippedCharge, newSize);
199 }
200
201 if (storageLayout_ & dslFlucQPosition) {
202 internalResize(flucQPos, newSize);
203 }
204
205 if (storageLayout_ & dslFlucQVelocity) {
206 internalResize(flucQVel, newSize);
207 }
208
209 if (storageLayout_ & dslFlucQForce) { internalResize(flucQFrc, newSize); }
210
211 if (storageLayout_ & dslSitePotential) {
212 internalResize(sitePotential, newSize);
213 }
214
215 size_ = newSize;
216 }
217
218 void DataStorage::reserve(std::size_t size) {
219 if (storageLayout_ & dslPosition) { position.reserve(size); }
220
221 if (storageLayout_ & dslVelocity) { velocity.reserve(size); }
222
223 if (storageLayout_ & dslForce) { force.reserve(size); }
224
225 if (storageLayout_ & dslAmat) { aMat.reserve(size); }
226
227 if (storageLayout_ & dslAngularMomentum) { angularMomentum.reserve(size); }
228
229 if (storageLayout_ & dslTorque) { torque.reserve(size); }
230
231 if (storageLayout_ & dslParticlePot) { particlePot.reserve(size); }
232
233 if (storageLayout_ & dslDensity) { density.reserve(size); }
234
235 if (storageLayout_ & dslFunctional) { functional.reserve(size); }
236
237 if (storageLayout_ & dslFunctionalDerivative) {
238 functionalDerivative.reserve(size);
239 }
240
241 if (storageLayout_ & dslDipole) { dipole.reserve(size); }
242
243 if (storageLayout_ & dslQuadrupole) { quadrupole.reserve(size); }
244
245 if (storageLayout_ & dslElectricField) { electricField.reserve(size); }
246
247 if (storageLayout_ & dslSkippedCharge) { skippedCharge.reserve(size); }
248
249 if (storageLayout_ & dslFlucQPosition) { flucQPos.reserve(size); }
250
251 if (storageLayout_ & dslFlucQVelocity) { flucQVel.reserve(size); }
252
253 if (storageLayout_ & dslFlucQForce) { flucQFrc.reserve(size); }
254
255 if (storageLayout_ & dslSitePotential) { sitePotential.reserve(size); }
256 }
257
258 void DataStorage::copy(int source, std::size_t num, std::size_t target) {
259 if (num + target > size_) {
260 // error
261 }
262
263 if (storageLayout_ & dslPosition) {
264 internalCopy(position, source, num, target);
265 }
266
267 if (storageLayout_ & dslVelocity) {
268 internalCopy(velocity, source, num, target);
269 }
270
271 if (storageLayout_ & dslForce) { internalCopy(force, source, num, target); }
272
273 if (storageLayout_ & dslAmat) { internalCopy(aMat, source, num, target); }
274
275 if (storageLayout_ & dslAngularMomentum) {
276 internalCopy(angularMomentum, source, num, target);
277 }
278
279 if (storageLayout_ & dslTorque) {
280 internalCopy(torque, source, num, target);
281 }
282
283 if (storageLayout_ & dslParticlePot) {
284 internalCopy(particlePot, source, num, target);
285 }
286
287 if (storageLayout_ & dslDensity) {
288 internalCopy(density, source, num, target);
289 }
290
291 if (storageLayout_ & dslFunctional) {
292 internalCopy(functional, source, num, target);
293 }
294
295 if (storageLayout_ & dslFunctionalDerivative) {
296 internalCopy(functionalDerivative, source, num, target);
297 }
298
299 if (storageLayout_ & dslDipole) {
300 internalCopy(dipole, source, num, target);
301 }
302
303 if (storageLayout_ & dslQuadrupole) {
304 internalCopy(quadrupole, source, num, target);
305 }
306
307 if (storageLayout_ & dslElectricField) {
308 internalCopy(electricField, source, num, target);
309 }
310
311 if (storageLayout_ & dslSkippedCharge) {
312 internalCopy(skippedCharge, source, num, target);
313 }
314
315 if (storageLayout_ & dslFlucQPosition) {
316 internalCopy(flucQPos, source, num, target);
317 }
318
319 if (storageLayout_ & dslFlucQVelocity) {
320 internalCopy(flucQVel, source, num, target);
321 }
322 if (storageLayout_ & dslFlucQForce) {
323 internalCopy(flucQFrc, source, num, target);
324 }
325
326 if (storageLayout_ & dslSitePotential) {
327 internalCopy(sitePotential, source, num, target);
328 }
329 }
330
331 int DataStorage::getStorageLayout() { return storageLayout_; }
332
334 storageLayout_ = layout;
335 resize(size_);
336 }
337
338 RealType* DataStorage::getArrayPointer(int whichArray) {
339 switch (whichArray) {
340 case dslPosition:
341 return internalGetArrayPointer(position);
342
343 case dslVelocity:
344 return internalGetArrayPointer(velocity);
345
346 case dslForce:
347 return internalGetArrayPointer(force);
348
349 case dslAmat:
350 return internalGetArrayPointer(aMat);
351
352 case dslAngularMomentum:
353 return internalGetArrayPointer(angularMomentum);
354
355 case dslTorque:
356 return internalGetArrayPointer(torque);
357
358 case dslParticlePot:
359 return internalGetArrayPointer(particlePot);
360
361 case dslDensity:
362 return internalGetArrayPointer(density);
363
364 case dslFunctional:
365 return internalGetArrayPointer(functional);
366
367 case dslFunctionalDerivative:
368 return internalGetArrayPointer(functionalDerivative);
369
370 case dslDipole:
371 return internalGetArrayPointer(dipole);
372
373 case dslQuadrupole:
374 return internalGetArrayPointer(quadrupole);
375
376 case dslElectricField:
377 return internalGetArrayPointer(electricField);
378
379 case dslSkippedCharge:
380 return internalGetArrayPointer(skippedCharge);
381
382 case dslFlucQPosition:
383 return internalGetArrayPointer(flucQPos);
384
385 case dslFlucQVelocity:
386 return internalGetArrayPointer(flucQVel);
387
388 case dslFlucQForce:
389 return internalGetArrayPointer(flucQFrc);
390
391 case dslSitePotential:
392 return internalGetArrayPointer(sitePotential);
393
394 default:
395 // error message
396 return NULL;
397 }
398 }
399
400 RealType* DataStorage::internalGetArrayPointer(std::vector<Vector3d>& v) {
401 if (v.empty()) {
402 return NULL;
403 } else {
404 return v[0].getArrayPointer();
405 }
406 }
407
408 RealType* DataStorage::internalGetArrayPointer(std::vector<Mat3x3d>& v) {
409 if (v.empty()) {
410 return NULL;
411 } else {
412 return v[0].getArrayPointer();
413 }
414 }
415
416 RealType* DataStorage::internalGetArrayPointer(std::vector<RealType>& v) {
417 if (v.empty()) {
418 return NULL;
419 } else {
420 return &(v[0]);
421 }
422 }
423
424 template<typename T>
425 void DataStorage::internalResize(std::vector<T>& v, std::size_t newSize) {
426 std::size_t oldSize = v.size();
427
428 if (oldSize == newSize) {
429 return;
430 } else if (oldSize < newSize) {
431 v.insert(v.end(), newSize - oldSize, T());
432 } else {
433 typename std::vector<T>::iterator i;
434 i = v.begin();
435 std::advance(i, newSize);
436 v.erase(i, v.end());
437 }
438 }
439
440 template<typename T>
441 void DataStorage::internalCopy(std::vector<T>& v, int source, std::size_t num,
442 std::size_t target) {
443 typename std::vector<T>::iterator first;
444 typename std::vector<T>::iterator last;
445 typename std::vector<T>::iterator result;
446
447 first = v.begin();
448 last = v.begin();
449 result = v.begin();
450
451 std::advance(first, source);
452 // STL algorithm use half opened range
453 std::advance(last, num + 1);
454 std::advance(result, target);
455
456 std::copy(first, last, result);
457 }
458
459 std::size_t DataStorage::getBytesPerStuntDouble(int layout) {
460 std::size_t bytes = 0;
461 if (layout & dslPosition) { bytes += sizeof(Vector3d); }
462 if (layout & dslVelocity) { bytes += sizeof(Vector3d); }
463 if (layout & dslForce) { bytes += sizeof(Vector3d); }
464 if (layout & dslAmat) { bytes += sizeof(RotMat3x3d); }
465 if (layout & dslAngularMomentum) { bytes += sizeof(Vector3d); }
466 if (layout & dslTorque) { bytes += sizeof(Vector3d); }
467 if (layout & dslParticlePot) { bytes += sizeof(RealType); }
468 if (layout & dslDensity) { bytes += sizeof(RealType); }
469 if (layout & dslFunctional) { bytes += sizeof(RealType); }
470 if (layout & dslFunctionalDerivative) { bytes += sizeof(RealType); }
471 if (layout & dslDipole) { bytes += sizeof(Vector3d); }
472 if (layout & dslQuadrupole) { bytes += sizeof(Mat3x3d); }
473 if (layout & dslElectricField) { bytes += sizeof(Vector3d); }
474 if (layout & dslSkippedCharge) { bytes += sizeof(RealType); }
475 if (layout & dslFlucQPosition) { bytes += sizeof(RealType); }
476 if (layout & dslFlucQVelocity) { bytes += sizeof(RealType); }
477 if (layout & dslFlucQForce) { bytes += sizeof(RealType); }
478 if (layout & dslSitePotential) { bytes += sizeof(RealType); }
479
480 return bytes;
481 }
482
483} // namespace OpenMD
void copy(int source, std::size_t num, std::size_t target)
Copies data inside DataStorage class.
vector< RealType > functional
electron density
int getStorageLayout()
Returns the storage layout.
void resize(std::size_t newSize)
Changes the size of this DataStorage.
vector< RealType > flucQFrc
fluctuating charge velocities
vector< RealType > particlePot
torque array
vector< RealType > sitePotential
fluctuating charge forces
vector< Mat3x3d > quadrupole
space-frame dipole vector
vector< RealType > functionalDerivative
density functional
vector< RealType > flucQPos
charge skipped during normal pairwise calculation
vector< Vector3d > velocity
position array
vector< RotMat3x3d > aMat
force array
vector< RealType > density
particle potential arrray
vector< RealType > skippedCharge
local electric field
void setStorageLayout(int layout)
Sets the storage layout.
std::size_t getSize()
return the size of this DataStorage.
static std::size_t getBytesPerStuntDouble(int layout)
electrostatic site potentials
vector< RealType > flucQVel
fluctuating charges
vector< Vector3d > torque
angular momentum array (body-fixed)
vector< Vector3d > force
velocity array
vector< Vector3d > electricField
space-frame quadrupole tensor
void reserve(std::size_t size)
Reallocates memory manually.
vector< Vector3d > dipole
derivative of functional
vector< Vector3d > angularMomentum
rotation matrix array
RealType * getArrayPointer(int whichArray)
Returns the pointer of internal array.
This basic Periodic Table class was originally taken from the data.cpp file in OpenBabel.