Matrix.hpp
Go to the documentation of this file.
1 /*
2 
3  This file is part of OpenFLUID software
4  Copyright(c) 2007, INRA - Montpellier SupAgro
5 
6 
7  == GNU General Public License Usage ==
8 
9  OpenFLUID is free software: you can redistribute it and/or modify
10  it under the terms of the GNU General Public License as published by
11  the Free Software Foundation, either version 3 of the License, or
12  (at your option) any later version.
13 
14  OpenFLUID is distributed in the hope that it will be useful,
15  but WITHOUT ANY WARRANTY; without even the implied warranty of
16  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17  GNU General Public License for more details.
18 
19  You should have received a copy of the GNU General Public License
20  along with OpenFLUID. If not, see <http://www.gnu.org/licenses/>.
21 
22 
23  == Other Usage ==
24 
25  Other Usage means a use of OpenFLUID that is inconsistent with the GPL
26  license, and requires a written agreement between You and INRA.
27  Licensees for Other Usage of OpenFLUID may use this file in accordance
28  with the terms contained in the written agreement between You and INRA.
29 
30 */
31 
32 
33 
34 /**
35  @file Matrix.hpp
36 
37  @author Jean-Christophe FABRE <jean-christophe.fabre@supagro.inra.fr>
38  */
39 
40 
41 #ifndef __OPENFLUID_CORE_MATRIX_HPP__
42 #define __OPENFLUID_CORE_MATRIX_HPP__
43 
44 
45 #include <openfluid/dllexport.hpp>
47 
48 
49 namespace openfluid { namespace core {
50 
51 
52 /**
53  Template class for matrix data
54 */
55 template <class T>
57 {
58  protected :
59 
60  T* m_Data;
61 
62  unsigned long m_ColsNbr;
63 
64  unsigned long m_RowsNbr;
65 
66  bool allocate(unsigned long ColsNbr, unsigned long RowsNbr);
67 
68  void init();
69 
70 
71  public :
72 
73  /**
74  Default constructor, creates an empty Matrix
75  */
76  Matrix();
77 
78  /**
79  Copy constructor
80  */
81  Matrix(const Matrix &Matrix);
82 
83  /**
84  Constructor, creates a Matrix containing Size elements
85  */
86  Matrix(unsigned long ColsNbr,unsigned long RowsNbr);
87 
88  /**
89  Constructor, creates a Matrix containing Size elements, initialized with value InitValue
90  */
91  Matrix(unsigned long ColsNbr,unsigned long RowsNbr, T InitValue);
92 
93  /**
94  Destructor
95  */
96  virtual ~Matrix()
97  { };
98 
99  /**
100  Returns the number of columns of the Matrix
101  @return number of columns
102  */
103  inline unsigned long getColsNbr() const
104  { return m_ColsNbr; };
105 
106  /**
107  Returns the number of rows of the Matrix
108  @return number of rows
109  */
110  inline unsigned long getRowsNbr() const { return m_RowsNbr; };
111 
112  /**
113  Returns the full size of the Matrix (number of columns x number of rows)
114  @return size of the Matrix
115  */
116  inline unsigned long getSize() const
117  { return (m_ColsNbr * m_RowsNbr); };
118 
119  /**
120  Returns the full size of the Matrix
121  */
122  inline unsigned long size() const
123  { return (m_ColsNbr * m_RowsNbr); };
124 
125 
126  /**
127  Returns a pointer to the content of the Matrix (like C arrays)
128  */
129  T* data() const
130  { return static_cast<T*>(m_Data); };
131 
132  /**
133  Sets data from a pointer to a content (like C arrays)
134  */
135  void setData(T* Data, unsigned long ColsNbr, unsigned long RowsNbr);
136 
137  /**
138  Returns the element of the Matrix for index Index
139  */
140  T getElement(unsigned long ColIndex, unsigned long RowIndex) const;
141 
142  /**
143  Returns the element of the Matrix for index Index
144  */
145  inline T at(unsigned long ColIndex, unsigned long RowIndex) const
146  { return getElement(ColIndex,RowIndex); };
147 
148  /**
149  Returns the element of the Matrix for index Index
150  */
151  inline T get(unsigned long ColIndex, unsigned long RowIndex) const
152  { return getElement(ColIndex,RowIndex); };
153 
154 
155  /**
156  Sets a new value for element at the given index
157  */
158  void setElement(unsigned long ColIndex, unsigned long RowIndex, T Element);
159 
160  /**
161  Sets a new value for element at the given index
162  */
163  inline void set(unsigned long ColIndex, unsigned long RowIndex, T Element)
164  { setElement(ColIndex,RowIndex,Element); };
165 
166  /**
167  Allocation operator
168  */
169  Matrix<T>& operator=(const Matrix &A);
170 
171  /**
172  Fills the Matrix with given value
173  */
174  void fill(const T& Val);
175 
176  /**
177  Clears the Matrix (empty and size is 0)
178  */
179  void clear();
180 
181 };
182 
183 
184 // =====================================================================
185 // =====================================================================
186 
187 
188 template <class T>
190  m_ColsNbr(0),m_RowsNbr(0)
191 {
192  init();
193 }
194 
195 
196 // =====================================================================
197 // =====================================================================
198 
199 
200 template <class T>
202 {
203  init();
204 
205  if (!allocate(A.m_ColsNbr,A.m_RowsNbr))
206  throw openfluid::base::FrameworkException(OPENFLUID_CODE_LOCATION,"Cannot allocate memory");
207 
208  std::copy(A.m_Data, A.m_Data + (A.m_ColsNbr*A.m_RowsNbr), m_Data);
209 }
210 
211 
212 // =====================================================================
213 // =====================================================================
214 
215 
216 template <class T>
217 Matrix<T>::Matrix(unsigned long ColsNbr, unsigned long RowsNbr)
218 {
219  init();
220 
221  if (!allocate(ColsNbr,RowsNbr))
222  throw openfluid::base::FrameworkException(OPENFLUID_CODE_LOCATION,"Cannot allocate memory");
223 
224  fill(0);
225 }
226 
227 
228 // =====================================================================
229 // =====================================================================
230 
231 
232 template <class T>
233 Matrix<T>::Matrix(unsigned long ColsNbr, unsigned long RowsNbr, T InitValue)
234 {
235  init();
236 
237  if (!allocate(ColsNbr,RowsNbr))
238  throw openfluid::base::FrameworkException(OPENFLUID_CODE_LOCATION,"Cannot allocate memory");
239 
240  fill(InitValue);
241 }
242 
243 
244 // =====================================================================
245 // =====================================================================
246 
247 
248 template <class T>
250 {
251  m_Data = nullptr;
252  m_ColsNbr = 0;
253  m_RowsNbr = 0;
254 }
255 
256 
257 // =====================================================================
258 // =====================================================================
259 
260 
261 template <class T>
262 bool Matrix<T>::allocate(unsigned long ColsNbr, unsigned long RowsNbr)
263 {
264  if (ColsNbr > 0 && RowsNbr > 0)
265  {
266  m_Data = new T[ColsNbr*RowsNbr];
267  if (m_Data)
268  {
269  m_RowsNbr = RowsNbr;
270  m_ColsNbr = ColsNbr;
271  }
272  else
273  return false;
274  }
275 
276  return true;
277 }
278 
279 // =====================================================================
280 // =====================================================================
281 
282 
283 template <class T>
284 void Matrix<T>::setData(T* Data, unsigned long ColsNbr, unsigned long RowsNbr)
285 {
286  clear();
287 
288  if (!allocate(ColsNbr,RowsNbr))
289  throw openfluid::base::FrameworkException(OPENFLUID_CODE_LOCATION,"Cannot allocate memory");
290 
291  std::copy(Data, Data + (ColsNbr*RowsNbr), m_Data);
292 }
293 
294 
295 // =====================================================================
296 // =====================================================================
297 
298 
299 template <class T>
300 T Matrix<T>::getElement(unsigned long ColIndex, unsigned long RowIndex) const
301 {
302  if (ColIndex >= m_ColsNbr || RowIndex >= m_RowsNbr)
303  throw openfluid::base::FrameworkException(OPENFLUID_CODE_LOCATION,"element access range error");
304 
305  return m_Data[ColIndex*m_RowsNbr+RowIndex];
306 }
307 
308 
309 // =====================================================================
310 // =====================================================================
311 
312 
313 template <class T>
314 void Matrix<T>::setElement(unsigned long ColIndex, unsigned long RowIndex, T Element)
315 {
316  if (ColIndex >= m_ColsNbr || RowIndex >= m_RowsNbr)
317  throw openfluid::base::FrameworkException(OPENFLUID_CODE_LOCATION,"element access range error");
318 
319  m_Data[ColIndex*m_RowsNbr+RowIndex] = Element;
320 }
321 
322 
323 
324 // =====================================================================
325 // =====================================================================
326 
327 template <class T>
329 {
330 
331  if (this == &A) return *this; // in case somebody tries assign array to itself
332 
333  clear();
334 
335  if (!allocate(A.m_ColsNbr,A.m_RowsNbr))
336  throw openfluid::base::FrameworkException(OPENFLUID_CODE_LOCATION,"Cannot allocate memory");
337 
338  std::copy(A.m_Data, A.m_Data + (A.m_ColsNbr*A.m_RowsNbr), m_Data);
339 
340  return *this;
341 }
342 
343 
344 // =====================================================================
345 // =====================================================================
346 
347 
348 template <class T>
349 void Matrix<T>::fill(const T& Val)
350 {
351  for (unsigned long i=0;i<m_RowsNbr;i++)
352  for (unsigned long j=0;j<m_ColsNbr;j++)
353  m_Data[i*m_ColsNbr+j] = Val;
354 }
355 
356 
357 // =====================================================================
358 // =====================================================================
359 
360 
361 template <class T>
363 {
364  delete [] m_Data;
365  init();
366 }
367 
368 
369 
370 } }
371 
372 #endif /* __OPENFLUID_CORE_MATRIX_HPP__ */
unsigned long getColsNbr() const
Definition: Matrix.hpp:103
void fill(const T &Val)
Definition: Matrix.hpp:349
Definition: Matrix.hpp:56
unsigned long getSize() const
Definition: Matrix.hpp:116
bool allocate(unsigned long ColsNbr, unsigned long RowsNbr)
Definition: Matrix.hpp:262
void clear()
Definition: Matrix.hpp:362
T * data() const
Definition: Matrix.hpp:129
unsigned long size() const
Definition: Matrix.hpp:122
unsigned long m_ColsNbr
Definition: Matrix.hpp:62
unsigned long getRowsNbr() const
Definition: Matrix.hpp:110
void setData(T *Data, unsigned long ColsNbr, unsigned long RowsNbr)
Definition: Matrix.hpp:284
Matrix()
Definition: Matrix.hpp:189
T * m_Data
Definition: Matrix.hpp:60
Definition: FrameworkException.hpp:50
Definition: ApplicationException.hpp:47
#define OPENFLUID_API
Definition: dllexport.hpp:87
virtual ~Matrix()
Definition: Matrix.hpp:96
unsigned long m_RowsNbr
Definition: Matrix.hpp:64
void setElement(unsigned long ColIndex, unsigned long RowIndex, T Element)
Definition: Matrix.hpp:314
T getElement(unsigned long ColIndex, unsigned long RowIndex) const
Definition: Matrix.hpp:300
Matrix< T > & operator=(const Matrix &A)
Definition: Matrix.hpp:328
T at(unsigned long ColIndex, unsigned long RowIndex) const
Definition: Matrix.hpp:145
void init()
Definition: Matrix.hpp:249