forked from ClimateGlobalChange/tempestremap
-
Notifications
You must be signed in to change notification settings - Fork 0
/
DataVector.h
236 lines (197 loc) · 4.54 KB
/
DataVector.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
///////////////////////////////////////////////////////////////////////////////
///
/// \file DataVector.h
/// \author Paul Ullrich
/// \version July 26, 2010
///
/// <remarks>
/// Copyright 2000-2010 Paul Ullrich
///
/// This file is distributed as part of the Tempest source code package.
/// Permission is granted to use, copy, modify and distribute this
/// source code and its documentation under the terms of the GNU General
/// Public License. This software is provided "as is" without express
/// or implied warranty.
/// </remarks>
#ifndef _DATAVECTOR_H_
#define _DATAVECTOR_H_
///////////////////////////////////////////////////////////////////////////////
#include "Exception.h"
#include <sstream>
#include <iostream>
#include <cstdlib>
#include <cstring>
///////////////////////////////////////////////////////////////////////////////
/// <summary>
/// A data vector is a datatype that stores data in a 1D structure.
/// Arithmetic operations are supported for this datatype.
/// </summary>
/// <warning>
/// Memory is allocated using malloc and deallocated using free, so no
/// calls will be made to the constructor or destructor of DataType. This
/// class is primarily designed to efficiently handle primitive types.
/// </warning>
template <typename DataType>
class DataVector {
public:
/// <summary>
/// Constructor.
/// </summary>
DataVector() :
m_sRows(0),
m_data(NULL)
{ }
/// <summary>
/// Constructor.
/// </summary>
DataVector(
unsigned int sRows
) :
m_sRows(0),
m_data(NULL)
{
Initialize(sRows);
}
/// <summary>
/// Copy constructor.
/// </summary>
DataVector(
const DataVector<DataType> & dv
) :
m_sRows(0),
m_data(NULL)
{
Assign(dv);
}
/// <summary>
/// Destructor.
/// </summary>
virtual ~DataVector() {
if (m_data != NULL) {
free(reinterpret_cast<void*>(m_data));
}
}
public:
/// <summary>
/// Determine if this DataVector is initialized.
/// </summary>
bool IsInitialized() const {
if (m_data == NULL) {
return false;
} else {
return true;
}
}
public:
/// <summary>
/// Deallocate data for this object.
/// </summary>
void Deinitialize() {
if (m_data != NULL) {
free(reinterpret_cast<void*>(m_data));
}
m_data = NULL;
m_sRows = 0;
}
/// <summary>
/// Allocate data for this object.
/// </summary>
void Initialize(
unsigned int sRows,
bool fAutoZero = true
) {
// Check for zero size
if (sRows == 0) {
Deinitialize();
return;
}
// No need to reallocate memory if this vector already has
// the correct dimensions.
if (m_sRows == sRows) {
// Auto zero
if (fAutoZero) {
Zero();
}
return;
}
// Deinitialize existing content
Deinitialize();
// Allocate memory
m_data = reinterpret_cast<DataType*>(
malloc(sRows * sizeof(DataType)));
if (m_data == NULL) {
_EXCEPTIONT("Out of memory.");
}
// Assign dimensions
m_sRows = sRows;
// Auto zero
if (fAutoZero) {
Zero();
}
}
public:
/// <summary>
/// Assignment operator.
/// </summary>
void Assign(const DataVector<DataType> & dv) {
// Check initialization status
if (!dv.IsInitialized()) {
Deinitialize();
return;
}
// Allocate memory
Initialize(dv.m_sRows, false);
// Copy data
memcpy(m_data, dv.m_data, m_sRows * sizeof(DataType));
}
/// <summary>
/// Assignment operator.
/// </summary>
DataVector & operator= (const DataVector<DataType> & dv) {
Assign(dv);
return (*this);
}
/// <summary>
/// Zero the data content of this object.
/// </summary>
void Zero() {
// Check initialization status
if (!IsInitialized()) {
_EXCEPTIONT(
"Attempted operation on uninitialized DataVector.");
}
// Set content to zero
memset(m_data, 0, m_sRows * sizeof(DataType));
}
public:
/// <summary>
/// Get the number of rows in this matrix.
/// </summary>
inline unsigned int GetRows() const {
return m_sRows;
}
public:
/// <summary>
/// Cast to an array.
/// </summary>
inline operator DataType*() {
return m_data;
}
/// <summary>
/// Cast to an array.
/// </summary>
inline operator const DataType*() const {
return m_data;
}
private:
/// <summary>
/// The number of rows in this matrix.
/// </summary>
unsigned int m_sRows;
/// <summary>
/// A pointer to the data associated with this matrix.
/// </summary>
DataType* m_data;
};
///////////////////////////////////////////////////////////////////////////////
#endif