Cantera  2.2.1
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
Array.h
Go to the documentation of this file.
1 /**
2  * @file Array.h Header file for class Cantera::Array2D
3  */
4 // Copyright 2001 California Institute of Technology
5 
6 
7 #ifndef CT_ARRAY_H
8 #define CT_ARRAY_H
9 
10 #include "utilities.h"
11 
12 #include <iostream>
13 #include <cstring>
14 
15 namespace Cantera
16 {
17 
18 //! A class for 2D arrays stored in column-major
19 //! (Fortran-compatible) form.
20 /*!
21  * In this form, the data entry for an n row, m col
22  * matrix is
23  * index = i + (n-1) * j
24  * where
25  * J(i,j) = data_start + index
26  * i = row
27  * j = column
28  */
29 class Array2D
30 {
31 public:
32  //! Type definition for the iterator class that is
33  //! can be used by Array2D types.
34  /*!
35  * this is just equal to vector_fp iterator.
36  */
37  typedef vector_fp::iterator iterator;
38 
39  //! Type definition for the const_iterator class that is
40  //! can be used by Array2D types.
41  /*!
42  * this is just equal to vector_fp const_iterator.
43  */
44  typedef vector_fp::const_iterator const_iterator;
45 
46  /**
47  * Default constructor. Create an empty array.
48  */
49  Array2D() :
50  m_data(0),
51  m_nrows(0),
52  m_ncols(0) {
53  }
54 
55  //! Constructor.
56  /*!
57  * Create an \c m by \c n array, and initialize
58  * all elements to \c v.
59  *
60  * @param m Number of rows
61  * @param n Number of columns
62  * @param v Default fill value. The default is 0.0
63  */
64  Array2D(const size_t m, const size_t n, const doublereal v = 0.0)
65  : m_data(0), m_nrows(m), m_ncols(n) {
66  m_data.resize(n*m);
67  std::fill(m_data.begin(), m_data.end(), v);
68  }
69 
70  //! Constructor.
71  /*!
72  * Create an \c m by \c n array, initialized with the contents
73  * of the array \c values.
74  *
75  * @param m Number of rows
76  * @param n Number of columns
77  * @param values Initial values of the array. Must be of length m*n,
78  * and stored in column-major order.
79  */
80  Array2D(const size_t m, const size_t n, const doublereal* values)
81  : m_data(0), m_nrows(m), m_ncols(n) {
82  m_data.resize(n*m);
83  std::copy(values, values + m_nrows*m_ncols, m_data.begin());
84  }
85 
86  //! Copy constructor
87  /*!
88  * @param y Array2D to make the copy from
89  */
90  Array2D(const Array2D& y) :
91  m_data(0),
92  m_nrows(0),
93  m_ncols(0) {
94  m_nrows = y.m_nrows;
95  m_ncols = y.m_ncols;
96  m_data.resize(m_nrows*m_ncols);
97  m_data = y.m_data;
98  }
99 
100  //! assignment operator
101  /*!
102  * @param y Array2D to get the values from
103  */
104  Array2D& operator=(const Array2D& y) {
105  if (&y == this) {
106  return *this;
107  }
108  m_nrows = y.m_nrows;
109  m_ncols = y.m_ncols;
110  m_data.resize(m_nrows*m_ncols);
111  m_data = y.m_data;
112  return *this;
113  }
114 
115  //! Resize the array, and fill the new entries with 'v'
116  /*!
117  * @param n This is the number of rows
118  * @param m This is the number of columns in the new matrix
119  * @param v Default fill value -> defaults to zero.
120  */
121  void resize(size_t n, size_t m, doublereal v = 0.0) {
122  m_nrows = n;
123  m_ncols = m;
124  m_data.resize(n*m, v);
125  }
126 
127  //! Copy the data from one array into another without doing any checking
128  /*!
129  * This differs from the assignment operator as no resizing is done and memcpy() is used.
130  * @param y Array to be copied
131  * @deprecated To be removed after Cantera 2.2.
132  */
133  void copyData(const Array2D& y) {
134  warn_deprecated("Array2D::copyData", "To be removed after Cantera 2.2.");
135  size_t n = sizeof(doublereal) * m_nrows * m_ncols;
136  (void) memcpy(DATA_PTR(m_data), y.ptrColumn(0), n);
137  }
138 
139  //! Append a column to the existing matrix using a std vector
140  /*!
141  * This operation will add a column onto the existing matrix.
142  *
143  * @param c This vector<doublereal> is the entries in the
144  * column to be added. It must have a length
145  * equal to m_nrows or greater.
146  */
147  void appendColumn(const vector_fp& c) {
148  m_ncols++;
149  m_data.resize(m_nrows*m_ncols);
150  size_t m;
151  for (m = 0; m < m_nrows; m++) {
152  value(m_ncols, m) = c[m];
153  }
154  }
155 
156  //! Append a column to the existing matrix
157  /*!
158  * This operation will add a column onto the existing matrix.
159  *
160  * @param c This vector of doubles is the entries in the
161  * column to be added. It must have a length
162  * equal to m_nrows or greater.
163  */
164  void appendColumn(const doublereal* const c) {
165  m_ncols++;
166  m_data.resize(m_nrows*m_ncols);
167  size_t m;
168  for (m = 0; m < m_nrows; m++) {
169  value(m_ncols, m) = c[m];
170  }
171  }
172 
173  //! Set the nth row to array rw
174  /*!
175  * @param n Index of the row to be changed
176  * @param rw Vector for the row. Must have a length of m_ncols.
177  */
178  void setRow(size_t n, const doublereal* const rw) {
179  for (size_t j = 0; j < m_ncols; j++) {
180  m_data[m_nrows*j + n] = rw[j];
181  }
182  }
183 
184  //! Get the nth row and return it in a vector
185  /*!
186  * @param n Index of the row to be returned.
187  * @param rw Return Vector for the operation.
188  * Must have a length of m_ncols.
189  */
190  void getRow(size_t n, doublereal* const rw) {
191  for (size_t j = 0; j < m_ncols; j++) {
192  rw[j] = m_data[m_nrows*j + n];
193  }
194  }
195 
196  //! Set the values in column m to those in array col
197  /*!
198  * A(i,m) = col(i)
199  *
200  * @param m Column to set
201  * @param col pointer to a col vector. Vector
202  * must have a length of m_nrows.
203  */
204  void setColumn(size_t m, doublereal* const col) {
205  for (size_t i = 0; i < m_nrows; i++) {
206  m_data[m_nrows*m + i] = col[i];
207  }
208  }
209 
210  //! Get the values in column m
211  /*!
212  * col(i) = A(i,m)
213  *
214  * @param m Column to set
215  * @param col pointer to a col vector that will be returned
216  */
217  void getColumn(size_t m, doublereal* const col) {
218  for (size_t i = 0; i < m_nrows; i++) {
219  col[i] = m_data[m_nrows*m + i];
220  }
221  }
222 
223  /**
224  * Destructor. Does nothing, since no memory allocated on the
225  * heap.
226  */
227  virtual ~Array2D() {}
228 
229  //! Evaluate z = a*x + y.
230  /*!
231  * This function evaluates the AXPY operation, and stores
232  * the result in the object's Array2D object.
233  * It's assumed that all 3 objects have the same dimensions,
234  * but no error checking is done.
235  *
236  * @param a scalar to multiply x with
237  * @param x First Array2D object to be used
238  * @param y Second Array2D object to be used
239  *
240  */
241  void axpy(doublereal a, const Array2D& x, const Array2D& y) {
242  iterator b = begin();
243  const_iterator xb = x.begin();
244  const_iterator yb = y.begin();
245  for (; b != end(); ++b, ++xb, ++yb) {
246  *b = a*(*xb) + *yb;
247  }
248  }
249 
250  //! Set all of the entries to zero
251  void zero() {
252  size_t nn = m_nrows * m_ncols;
253  if (nn > 0) {
254  /*
255  * Using memset is the fastest way to zero a contiguous
256  * section of memory.
257  */
258  (void) memset((void*) &m_data[0], 0, nn * sizeof(doublereal));
259  }
260  }
261 
262  //! Allows setting elements using the syntax A(i,j) = x.
263  /*!
264  * @param i row index
265  * @param j column index.
266  *
267  * @return Returns a reference to A(i,j) which may be assigned.
268  */
269  doublereal& operator()(size_t i, size_t j) {
270  return value(i,j);
271  }
272 
273 
274  //! Allows retrieving elements using the syntax x = A(i,j).
275  /*!
276  * @param i Index for the row to be retrieved
277  * @param j Index for the column to be retrieved.
278  *
279  * @return Returns the value of the matrix entry
280  */
281  doublereal operator()(size_t i, size_t j) const {
282  return value(i,j);
283  }
284 
285  //! Returns a changeable reference to position in the matrix
286  /*!
287  * This is a key entry. Returns a reference to the matrix's (i,j)
288  * element. This may be used as an L value.
289  *
290  * @param i The row index
291  * @param j The column index
292  *
293  * @return Returns a changeable reference to the matrix entry
294  */
295  doublereal& value(size_t i, size_t j) {
296  return m_data[m_nrows*j + i];
297  }
298 
299  //! Returns the value of a single matrix entry
300  /*!
301  * This is a key entry. Returns the value of the matrix position (i,j)
302  * element.
303  *
304  * @param i The row index
305  * @param j The column index
306  */
307  doublereal value(size_t i, size_t j) const {
308  return m_data[m_nrows*j + i];
309  }
310 
311  /// Number of rows
312  size_t nRows() const {
313  return m_nrows;
314  }
315 
316  /// Number of columns
317  size_t nColumns() const {
318  return m_ncols;
319  }
320 
321  /// Return an iterator pointing to the first element
323  return m_data.begin();
324  }
325 
326  /// Return an iterator pointing past the last element
328  return m_data.end();
329  }
330 
331  /// Return a const iterator pointing to the first element
333  return m_data.begin();
334  }
335 
336  /// Return a const iterator pointing to past the last element
337  const_iterator end() const {
338  return m_data.end();
339  }
340 
341  /// Return a reference to the data vector
343  return m_data;
344  }
345 
346  /// Return a const reference to the data vector
347  const vector_fp& data() const {
348  return m_data;
349  }
350 
351  //! Return a pointer to the top of column j, columns are contiguous
352  //! in memory
353  /*!
354  * @param j Value of the column
355  *
356  * @return Returns a pointer to the top of the column
357  */
358  doublereal* ptrColumn(size_t j) {
359  return &(m_data[m_nrows*j]);
360  }
361 
362  //! Return a const pointer to the top of column j, columns are contiguous
363  //! in memory
364  /*!
365  * @param j Value of the column
366  *
367  * @return Returns a const pointer to the top of the column
368  */
369  const doublereal* ptrColumn(size_t j) const {
370  return &(m_data[m_nrows*j]);
371  }
372 
373 protected:
374  //! Data stored in a single array
376 
377  //! Number of rows
378  size_t m_nrows;
379 
380  //! Number of columns
381  size_t m_ncols;
382 };
383 
384 //! Output the current contents of the Array2D object
385 /*!
386  * Example of usage:
387  * s << m << endl;
388  *
389  * @param s Reference to the ostream to write to
390  * @param m Object of type Array2D that you are querying
391  *
392  * @return Returns a reference to the ostream.
393  */
394 inline std::ostream& operator<<(std::ostream& s, const Array2D& m)
395 {
396  size_t nr = m.nRows();
397  size_t nc = m.nColumns();
398  size_t i,j;
399  for (i = 0; i < nr; i++) {
400  for (j = 0; j < nc; j++) {
401  s << m(i,j) << ", ";
402  }
403  s << std::endl;
404  }
405  return s;
406 }
407 
408 //! Overload the times equals operator for multiplication
409 //! of a matrix and a scalar.
410 /*!
411  * Scaled every element of the matrix by the scalar input
412  *
413  * @param m Matrix
414  * @param a scalar
415  */
416 inline void operator*=(Array2D& m, doublereal a)
417 {
418  scale(m.begin(), m.end(), m.begin(), a);
419 }
420 
421 //! Overload the plus equals operator for addition
422 //! of one matrix with another
423 /*!
424  * Adds each element of the second matrix into the first
425  * matrix
426  *
427  * @param x First matrix
428  * @param y Second matrix, which is a const
429  */
430 inline void operator+=(Array2D& x, const Array2D& y)
431 {
432  sum_each(x.begin(), x.end(), y.begin());
433 }
434 
435 }
436 
437 #endif
Array2D(const Array2D &y)
Copy constructor.
Definition: Array.h:90
size_t nRows() const
Number of rows.
Definition: Array.h:312
const vector_fp & data() const
Return a const reference to the data vector.
Definition: Array.h:347
vector_fp m_data
Data stored in a single array.
Definition: Array.h:375
Array2D()
Default constructor.
Definition: Array.h:49
void resize(size_t n, size_t m, doublereal v=0.0)
Resize the array, and fill the new entries with 'v'.
Definition: Array.h:121
Various templated functions that carry out common vector operations (see Templated Utility Functions)...
Array2D & operator=(const Array2D &y)
assignment operator
Definition: Array.h:104
void appendColumn(const vector_fp &c)
Append a column to the existing matrix using a std vector.
Definition: Array.h:147
void operator*=(Array2D &m, doublereal a)
Overload the times equals operator for multiplication of a matrix and a scalar.
Definition: Array.h:416
void warn_deprecated(const std::string &method, const std::string &extra)
Print a warning indicating that method is deprecated.
Definition: global.cpp:78
iterator end()
Return an iterator pointing past the last element.
Definition: Array.h:327
void copyData(const Array2D &y)
Copy the data from one array into another without doing any checking.
Definition: Array.h:133
doublereal value(size_t i, size_t j) const
Returns the value of a single matrix entry.
Definition: Array.h:307
doublereal * ptrColumn(size_t j)
Return a pointer to the top of column j, columns are contiguous in memory.
Definition: Array.h:358
void setRow(size_t n, const doublereal *const rw)
Set the nth row to array rw.
Definition: Array.h:178
void axpy(doublereal a, const Array2D &x, const Array2D &y)
Evaluate z = a*x + y.
Definition: Array.h:241
A class for 2D arrays stored in column-major (Fortran-compatible) form.
Definition: Array.h:29
void appendColumn(const doublereal *const c)
Append a column to the existing matrix.
Definition: Array.h:164
void getColumn(size_t m, doublereal *const col)
Get the values in column m.
Definition: Array.h:217
vector_fp::iterator iterator
Type definition for the iterator class that is can be used by Array2D types.
Definition: Array.h:37
Array2D(const size_t m, const size_t n, const doublereal v=0.0)
Constructor.
Definition: Array.h:64
size_t nColumns() const
Number of columns.
Definition: Array.h:317
doublereal operator()(size_t i, size_t j) const
Allows retrieving elements using the syntax x = A(i,j).
Definition: Array.h:281
size_t m_ncols
Number of columns.
Definition: Array.h:381
size_t m_nrows
Number of rows.
Definition: Array.h:378
Array2D(const size_t m, const size_t n, const doublereal *values)
Constructor.
Definition: Array.h:80
vector_fp & data()
Return a reference to the data vector.
Definition: Array.h:342
vector_fp::const_iterator const_iterator
Type definition for the const_iterator class that is can be used by Array2D types.
Definition: Array.h:44
doublereal & value(size_t i, size_t j)
Returns a changeable reference to position in the matrix.
Definition: Array.h:295
void operator+=(Array2D &x, const Array2D &y)
Overload the plus equals operator for addition of one matrix with another.
Definition: Array.h:430
doublereal & operator()(size_t i, size_t j)
Allows setting elements using the syntax A(i,j) = x.
Definition: Array.h:269
void sum_each(OutputIter x_begin, OutputIter x_end, InputIter y_begin)
Increment each entry in x by the corresponding entry in y.
Definition: utilities.h:399
std::vector< double > vector_fp
Turn on the use of stl vectors for the basic array type within cantera Vector of doubles.
Definition: ct_defs.h:157
void scale(InputIter begin, InputIter end, OutputIter out, S scale_factor)
Multiply elements of an array by a scale factor.
Definition: utilities.h:158
const doublereal * ptrColumn(size_t j) const
Return a const pointer to the top of column j, columns are contiguous in memory.
Definition: Array.h:369
const_iterator begin() const
Return a const iterator pointing to the first element.
Definition: Array.h:332
iterator begin()
Return an iterator pointing to the first element.
Definition: Array.h:322
#define DATA_PTR(vec)
Creates a pointer to the start of the raw data for a vector.
Definition: ct_defs.h:36
void getRow(size_t n, doublereal *const rw)
Get the nth row and return it in a vector.
Definition: Array.h:190
void zero()
Set all of the entries to zero.
Definition: Array.h:251
virtual ~Array2D()
Destructor.
Definition: Array.h:227
const_iterator end() const
Return a const iterator pointing to past the last element.
Definition: Array.h:337
void setColumn(size_t m, doublereal *const col)
Set the values in column m to those in array col.
Definition: Array.h:204