casacore
Loading...
Searching...
No Matches
ArrayBase.h
Go to the documentation of this file.
1//# ArrayBase.h: Non-templated base class for templated Array class
2//# Copyright (C) 1993,1994,1995,1996,1997,1998,1999,2000,2001,2002,2003
3//# Associated Universities, Inc. Washington DC, USA,
4//#
5//# This library is free software; you can redistribute it and/or modify it
6//# under the terms of the GNU Library General Public License as published by
7//# the Free Software Foundation; either version 2 of the License, or (at your
8//# option) any later version.
9//#
10//# This library is distributed in the hope that it will be useful, but WITHOUT
11//# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12//# FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public
13//# License for more details.
14//#
15//# You should have received a copy of the GNU Library General Public License
16//# along with this library; if not, write to the Free Software Foundation,
17//# Inc., 675 Massachusetts Ave, Cambridge, MA 02139, USA.
18//#
19//# Correspondence concerning AIPS++ should be addressed as follows:
20//# Internet email: casa-feedback@nrao.edu.
21//# Postal address: AIPS++ Project Office
22//# National Radio Astronomy Observatory
23//# 520 Edgemont Road
24//# Charlottesville, VA 22903-2475 USA
25
26#ifndef CASA_ARRAYBASE_2_H
27#define CASA_ARRAYBASE_2_H
28
29//# Includes
30#include "IPosition.h"
31
32#include <memory>
33
34namespace casacore { //# NAMESPACE CASACORE - BEGIN
35
36//# Forward declarations.
38class Slicer;
39
40
41// <summary>
42// A global enum used by some Array constructors.
43// </summary>
44// <synopsis>
45// StorageInitPolicy is used in functions where an array is formed from
46// a shape and an ordinary pointer. This enum should be in Array but that
47// causes gcc to be unhappy.
48// </synopsis>
50 // COPY is used when an internal copy of the storage is to be made.
51 // The array is NOT responsible for deleting the external storage.
53 // TAKE_OVER is used to indicate that the Array should just use the
54 // external storage (i.e., no copy is made). The Array class is now
55 // responsible for deleting the storage (hence it must have come from
56 // a call to new[]).
58 // Share means that the Array will just use the pointer (no copy), however
59 // the Array will NOT delete it upon destruction.
61
62
63// <summary>
64// Non-templated base class for templated Array class.
65// </summary>
66
67// ArrayBase is only used to factor out common code from the templated
68// Array class.
69
71{
72public:
73 ArrayBase() noexcept;
74
75 // Create an array of the given shape, i.e. after construction
76 // array.ndim() == shape.nelements() and array.shape() == shape.
77 // The origin of the Array is zero.
78 explicit ArrayBase (const IPosition& shape);
79
80 // Copy constructor.
81 ArrayBase (const ArrayBase& other);
82
83 ArrayBase (ArrayBase&& source) noexcept;
84
85 // Assignment.
87
88 ArrayBase& operator=(const ArrayBase&) = delete;
89
90 ArrayBase& operator=(ArrayBase&&) noexcept;
91
92 // Destructor.
93 virtual ~ArrayBase() noexcept;
94
95 // The dimensionality of this array.
96 size_t ndim() const
97 { return ndimen_p; }
98
99 // How many elements does this array have? Product of all axis lengths.
100 // <group>
101 size_t nelements() const
102 { return nels_p; }
103 size_t size() const
104 { return nels_p; }
105 // </group>
106
107 // Is the array empty (i.e. no elements)?
108 bool empty() const
109 { return nels_p == 0; }
110
111 // Are the array data contiguous?
112 // If they are not contiguous, <src>getStorage</src> (see below)
113 // needs to make a copy.
114 bool contiguousStorage() const
115 { return contiguous_p; }
116
117 // Check to see if the Array is consistent. This is about the same thing
118 // as checking for invariants. If AIPS_DEBUG is defined, this is invoked
119 // after construction and on entry to most member functions.
120 virtual bool ok() const;
121
122 // The length of each axis.
123 const IPosition& shape() const
124 { return length_p; }
125
126 // A convenience function: endPosition(i) = shape(i) - 1; i.e. this
127 // is the IPosition of the last element of the Array.
129
130 // Return steps to be made if stepping one element in a dimension.
131 // This is the 'physical' step, thus it also works correctly for
132 // non-contiguous arrays. E.g. <src>data() + steps(0)</src> gives
133 // the second element of the first axis.
134 const IPosition& steps() const
135 { return steps_p; }
136
137 // Array version for major change (used by ArrayIO).
138 // enum did not work properly with cfront 3.0.1), so replaced
139 // by a static inline function. Users won't normally use this.
140 static unsigned arrayVersion()
141 {return 3;}
142
143 // Make an empty array of the same type.
144 // <br>The default implementation in ArrayBase throws an exception.
145 virtual std::unique_ptr<ArrayBase> makeArray() const;
146
147 // Resize the array and optionally copy the values.
148 // <br>The default implementation in ArrayBase throws an exception.
149 virtual void resize(const IPosition &newShape, bool copyValues=false);
150
151 // Resize the array and optionally copy the values.
152 // <br>The default implementation in ArrayBase throws an exception.
153 //virtual void resize(const IPosition &newShape, bool copyValues, ArrayInitPolicy policy);
154
155 // Create an ArrayIterator object of the correct type.
156 // This is implemented in the derived Array classes.
157 // <br>The default implementation in ArrayBase throws an exception.
158 virtual std::unique_ptr<ArrayPositionIterator> makeIterator (size_t byDim) const;
159
160 // Get a reference to a section of an array.
161 // This is the same as Array<T>::operator(), but without having to know
162 // the exact template type.
163 // <br>The default implementation in ArrayBase throws an exception.
164 virtual std::unique_ptr<ArrayBase> getSection (const Slicer&) const;
165
166 // Assign the source array to this array.
167 // If <src>checkType==true</src>, it is checked if the underlying template
168 // types match. Otherwise, it is only checked in debug mode (for performance).
169 // <br>The default implementation in ArrayBase throws an exception.
170 virtual void assignBase (const ArrayBase& source, bool checkType=true);
171
172 // The following functions behave the same as the corresponding getStorage
173 // functions in the derived templated Array class.
174 // They handle a pointer to a contiguous block of array data.
175 // If the array is not contiguous, a copy is used to make it contiguous.
176 // <group>
177 virtual void* getVStorage (bool& deleteIt);
178 virtual const void* getVStorage (bool& deleteIt) const;
179 virtual void putVStorage(void*& storage, bool deleteAndCopy);
180 virtual void freeVStorage(const void*& storage, bool deleteIt) const;
181 // <group>
182
183protected:
184 // For subclasses, this move constructor allows the moved-from object to
185 // obtain a given shape after resizing. This way, e.g. a source Matrix can
186 // still kee a dimensionality of 2.
187 ArrayBase(ArrayBase&& source, const IPosition& shapeForSource) noexcept;
188
189 void swap(ArrayBase& source) noexcept;
190
191 // Either reforms the array if size permits or resizes it to the new shape.
192 // Implementation of Array<T>::reformOrResize (slightly different signature).
193
194 bool reformOrResize (const IPosition & newShape,
195 bool resizeIfNeeded,
196 size_t nReferences,
197 long long nElementsAllocated,
198 bool copyDataIfNeeded,
199 size_t resizePercentage);
200
201 // Determine if the storage of a subset is contiguous.
203
204 // Check if the shape of a vector is correct. If possible, adjust if not.
205 // It is possible if at most one axis has length > 1.
207
208 // Check if the shape of a matrix is correct. Adjust it if smaller.
210
211 // Check if the shape of a cube is correct. Adjust it if smaller.
213
214 // Reform the array to a shape with the same nr of elements. If nonStrict then
215 // caller assumes responsibility for not overrunning storage (avoid or use with extreme care).
216 void baseReform (ArrayBase& tmp, const IPosition& shape, bool strict=true) const;
217
218 // Remove the degenerate axes from the Array object.
219 // This is the implementation of the nonDegenerate functions.
220 // It has a different name to be able to make it virtual without having
221 // the "hide virtual function" message when compiling derived classes.
222 void baseNonDegenerate (const ArrayBase& other, const IPosition& ignoreAxes);
223
224 // These member functions return an Array reference with the specified
225 // number of extra axes, all of length one, appended to the end of the
226 // Array. Note that the <src>reform</src> function can also be
227 // used to add extra axes.
228 void baseAddDegenerate (ArrayBase&, size_t numAxes);
229
230 // Make a subset of an array.
231 // It checks if start,end,incr are within the array limits.
232 // It returns the offset of the subset in the (original) array.
233 size_t makeSubset (ArrayBase& out,
234 const IPosition& b,
235 const IPosition& e,
236 const IPosition& i);
237
238 // Set the length and stride such that the diagonal of the matrices
239 // defined by two consecutive axes is formed.
240 // <src>diag</src> == 0 indicates the main diagonal, >0 above, <0 below.
241 // It returns the offset of the diagonal in the (original) array.
242 size_t makeDiagonal (size_t firstAxis, long long diag);
243
244 // Are the shapes identical?
245 bool conform2 (const ArrayBase& other) const
246 { return length_p.isEqual (other.length_p); }
247
248 // Make the indexing step sizes.
250
251 // Helper function for templated Vector class.
252 // It returns if this and other are conformant.
253 bool copyVectorHelper (const ArrayBase& other);
254
255public:
256 // Various helper functions.
257 // <group>
258 void validateConformance (const ArrayBase&) const;
259 void validateIndex (const IPosition&) const;
260 void validateIndex (size_t index) const;
261 void validateIndex (size_t index1, size_t index2) const;
262 void validateIndex (size_t index1, size_t index2, size_t index3) const;
263 // </group>
264
265protected:
266 // Number of elements in the array. Cached rather than computed.
267 size_t nels_p;
268 // Dimensionality of the array.
269 size_t ndimen_p;
270 // Are the data contiguous?
272 // Used to hold the shape, increment into the underlying storage
273 // and originalLength of the array.
275 // Used to hold the step to next element in each dimension.
277};
278
279
280// <summary> General global functions for Arrays. </summary>
281// <reviewed reviewer="UNKNOWN" date="before2004/08/25" tests="tArray">
282//
283// <prerequisite>
284// <li> <linkto class=Array>Array</linkto>
285// </prerequisite>
286//
287// <synopsis>
288// These are generally useful global functions which operate on all
289// Arrays.
290// </synopsis>
291//
292// <linkfrom anchor="Array general global functions" classes="Array Vector Matrix Cube">
293// <here>Array general global functions</here> -- General global functions
294// for Arrays.
295// </linkfrom>
296//
297// <group name="Array general global functions">
298
299//
300// What is the volume of an N-dimensional array.
301// Shape[0]*Shape[1]*...*Shape[N-1]. An Array helper function.
302//# Implemented in Array2.cc.
303size_t ArrayVolume (size_t Ndim, const int* Shape);
304
305//
306// What is the linear index into an "Ndim" dimensional array of the given
307// "Shape", "Origin", and "Increment" for a given IPosition Index.
308// An Array helper function.
309// <group>
310//# Implemented in Array2.cc.
311size_t ArrayIndexOffset (size_t Ndim, const ssize_t* Shape,
312 const ssize_t* Origin, const ssize_t* Inc,
313 const IPosition& Index);
314size_t ArrayIndexOffset (size_t Ndim, const ssize_t* Shape,
315 const ssize_t* Inc, const IPosition& Index);
316// </group>
317
318// Function to check the shapes. It throws an exception if not equal.
319// <group>
320void throwArrayShapes (const IPosition& shape1,
321 const IPosition& shape2,
322 const char* name);
323inline void checkArrayShapes (const ArrayBase& left, const ArrayBase& right,
324 const char* name)
325{
326 if (! left.shape().isEqual (right.shape())) {
327 throwArrayShapes (left.shape(), right.shape(), name);
328 }
329}
330// </group>
331
332// </group>
333
334} //# NAMESPACE CASACORE - END
335
336#endif
Non-templated base class for templated Array class.
Definition ArrayBase.h:71
virtual bool ok() const
Check to see if the Array is consistent.
void validateIndex(size_t index1, size_t index2, size_t index3) const
static unsigned arrayVersion()
Array version for major change (used by ArrayIO).
Definition ArrayBase.h:140
void validateConformance(const ArrayBase &) const
Various helper functions.
ArrayBase & assign(const ArrayBase &)
Assignment.
void baseNonDegenerate(const ArrayBase &other, const IPosition &ignoreAxes)
Remove the degenerate axes from the Array object.
void baseReform(ArrayBase &tmp, const IPosition &shape, bool strict=true) const
Reform the array to a shape with the same nr of elements.
bool copyVectorHelper(const ArrayBase &other)
Helper function for templated Vector class.
virtual const void * getVStorage(bool &deleteIt) const
const IPosition & steps() const
Return steps to be made if stepping one element in a dimension.
Definition ArrayBase.h:134
void checkMatrixShape()
Check if the shape of a matrix is correct.
ArrayBase(ArrayBase &&source, const IPosition &shapeForSource) noexcept
For subclasses, this move constructor allows the moved-from object to obtain a given shape after resi...
size_t ndim() const
The dimensionality of this array.
Definition ArrayBase.h:96
size_t nels_p
Number of elements in the array.
Definition ArrayBase.h:267
void swap(ArrayBase &source) noexcept
void validateIndex(const IPosition &) const
ArrayBase() noexcept
virtual void assignBase(const ArrayBase &source, bool checkType=true)
Assign the source array to this array.
size_t nelements() const
How many elements does this array have?
Definition ArrayBase.h:101
virtual std::unique_ptr< ArrayBase > getSection(const Slicer &) const
Get a reference to a section of an array.
size_t size() const
Definition ArrayBase.h:103
virtual std::unique_ptr< ArrayBase > makeArray() const
Make an empty array of the same type.
size_t makeSubset(ArrayBase &out, const IPosition &b, const IPosition &e, const IPosition &i)
Make a subset of an array.
size_t ndimen_p
Dimensionality of the array.
Definition ArrayBase.h:269
bool contiguous_p
Are the data contiguous?
Definition ArrayBase.h:271
void baseAddDegenerate(ArrayBase &, size_t numAxes)
These member functions return an Array reference with the specified number of extra axes,...
virtual void freeVStorage(const void *&storage, bool deleteIt) const
IPosition originalLength_p
Definition ArrayBase.h:274
void baseMakeSteps()
Make the indexing step sizes.
bool reformOrResize(const IPosition &newShape, bool resizeIfNeeded, size_t nReferences, long long nElementsAllocated, bool copyDataIfNeeded, size_t resizePercentage)
Either reforms the array if size permits or resizes it to the new shape.
bool contiguousStorage() const
Are the array data contiguous?
Definition ArrayBase.h:114
bool empty() const
Is the array empty (i.e.
Definition ArrayBase.h:108
void validateIndex(size_t index1, size_t index2) const
const IPosition & shape() const
The length of each axis.
Definition ArrayBase.h:123
void validateIndex(size_t index) const
IPosition length_p
Used to hold the shape, increment into the underlying storage and originalLength of the array.
Definition ArrayBase.h:274
virtual void * getVStorage(bool &deleteIt)
The following functions behave the same as the corresponding getStorage functions in the derived temp...
size_t makeDiagonal(size_t firstAxis, long long diag)
Set the length and stride such that the diagonal of the matrices defined by two consecutive axes is f...
virtual void resize(const IPosition &newShape, bool copyValues=false)
Resize the array and optionally copy the values.
void checkVectorShape()
Check if the shape of a vector is correct.
virtual std::unique_ptr< ArrayPositionIterator > makeIterator(size_t byDim) const
Resize the array and optionally copy the values.
virtual void putVStorage(void *&storage, bool deleteAndCopy)
IPosition steps_p
Used to hold the step to next element in each dimension.
Definition ArrayBase.h:276
bool conform2(const ArrayBase &other) const
Are the shapes identical?
Definition ArrayBase.h:245
IPosition endPosition() const
A convenience function: endPosition(i) = shape(i) - 1; i.e.
void checkCubeShape()
Check if the shape of a cube is correct.
bool isStorageContiguous() const
Determine if the storage of a subset is contiguous.
bool isEqual(const IPosition &other) const
Element-by-element comparison for equality.
StorageInitPolicy
Definition ArrayBase.h:49
size_t ArrayVolume(size_t Ndim, const int *Shape)
General global functions for Arrays.
@ COPY
COPY is used when an internal copy of the storage is to be made.
Definition ArrayBase.h:52
@ SHARE
Share means that the Array will just use the pointer (no copy), however the Array will NOT delete it ...
Definition ArrayBase.h:60
@ TAKE_OVER
TAKE_OVER is used to indicate that the Array should just use the external storage (i....
Definition ArrayBase.h:57
this file contains all the compiler specific defines
Definition mainpage.dox:28
void checkArrayShapes(const ArrayBase &left, const ArrayBase &right, const char *name)
Definition ArrayBase.h:323
size_t ArrayIndexOffset(size_t Ndim, const ssize_t *Shape, const ssize_t *Origin, const ssize_t *Inc, const IPosition &Index)
What is the linear index into an "Ndim" dimensional array of the given "Shape", "Origin",...
String name() const
Return the name of the field.
void throwArrayShapes(const IPosition &shape1, const IPosition &shape2, const char *name)
Function to check the shapes.