core/Matrix.hpp
Go to the documentation of this file.
00001 /*
00002 
00003   This file is part of OpenFLUID software
00004   Copyright(c) 2007, INRA - Montpellier SupAgro
00005 
00006 
00007  == GNU General Public License Usage ==
00008 
00009   OpenFLUID is free software: you can redistribute it and/or modify
00010   it under the terms of the GNU General Public License as published by
00011   the Free Software Foundation, either version 3 of the License, or
00012   (at your option) any later version.
00013 
00014   OpenFLUID is distributed in the hope that it will be useful,
00015   but WITHOUT ANY WARRANTY; without even the implied warranty of
00016   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00017   GNU General Public License for more details.
00018 
00019   You should have received a copy of the GNU General Public License
00020   along with OpenFLUID. If not, see <http://www.gnu.org/licenses/>.
00021 
00022 
00023  == Other Usage ==
00024 
00025   Other Usage means a use of OpenFLUID that is inconsistent with the GPL
00026   license, and requires a written agreement between You and INRA.
00027   Licensees for Other Usage of OpenFLUID may use this file in accordance
00028   with the terms contained in the written agreement between You and INRA.
00029   
00030 */
00031 
00032 
00033 
00034 /**
00035   \file Matrix.hpp
00036   \brief Header of ...
00037 
00038   \author Jean-Christophe FABRE <fabrejc@supagro.inra.fr>
00039  */
00040 
00041 
00042 #ifndef __MATRIX_HPP___
00043 #define __MATRIX_HPP___
00044 
00045 
00046 
00047 #include <iostream>
00048 #include <openfluid/dllexport.hpp>
00049 #include <openfluid/base/FrameworkException.hpp>
00050 #include <boost/multi_array.hpp>
00051 
00052 namespace openfluid { namespace core {
00053 
00054 
00055 /**
00056   Template class for matrix data
00057 */
00058 template <class T>
00059 class DLLEXPORT Matrix
00060 {
00061   protected :
00062 
00063     boost::multi_array<T, 2> m_Data;
00064 
00065     unsigned long m_ColsNbr;
00066 
00067     unsigned long m_RowsNbr;
00068 
00069 
00070   public :
00071 
00072     /**
00073       Default constructor, creates an empty Matrix
00074     */
00075     Matrix();
00076 
00077     /**
00078       Copy constructor
00079      */
00080     Matrix(const Matrix &Matrix);
00081 
00082     /**
00083       Constructor, creates a Matrix containing Size elements
00084     */
00085     Matrix(unsigned long ColsNbr,unsigned long RowsNbr);
00086 
00087     /**
00088       Constructor, creates a Matrix containing Size elements, initialized with value InitValue
00089     */
00090     Matrix(unsigned long ColsNbr,unsigned long RowsNbr, T InitValue);
00091 
00092     /**
00093       Destructor
00094     */
00095     virtual ~Matrix() {};
00096 
00097     /**
00098       Returns the number of columns of the Matrix
00099       @return number of columns
00100     */
00101     inline unsigned long getColsNbr() const { return m_ColsNbr; };
00102 
00103     /**
00104       Returns the number of rows of the Matrix
00105       @return number of rows
00106     */
00107     inline unsigned long getRowsNbr() const { return m_RowsNbr; };
00108 
00109     /**
00110       Returns the full size of the Matrix (number of columns x number of rows)
00111       @return size of the Matrix
00112     */
00113     inline unsigned long getSize() const { return (m_ColsNbr * m_RowsNbr); };
00114 
00115     /**
00116       Returns the full size of the Matrix
00117     */
00118     inline unsigned long size() const { return (m_ColsNbr * m_RowsNbr); };
00119 
00120 
00121     /**
00122       Returns a pointer to the content of the Matrix (like C arrays)
00123     */
00124     T* getData() const { return (T*)(m_Data.data()); };
00125 
00126     /**
00127       Sets data from a pointer to a content (like C arrays)
00128     */
00129     void setData(T* Data);
00130 
00131     /**
00132       Returns the element of the Matrix for index Index
00133     */
00134     T getElement(unsigned long ColIndex, unsigned long RowIndex) const;
00135 
00136     /**
00137       Returns the element of the Matrix for index Index
00138     */
00139     inline T at(unsigned long ColIndex, unsigned long RowIndex) const { return getElement(ColIndex,RowIndex); };
00140 
00141     /**
00142       Returns the element of the Matrix for index Index
00143     */
00144     inline T get(unsigned long ColIndex, unsigned long RowIndex) const { return getElement(ColIndex,RowIndex); };
00145 
00146 
00147     /**
00148       Sets a new value for element at the given index
00149     */
00150     void setElement(unsigned long ColIndex, unsigned long RowIndex, T Element);
00151 
00152     /**
00153       Sets a new value for element at the given index
00154     */
00155     inline void set(unsigned long ColIndex, unsigned long RowIndex, T Element) { setElement(ColIndex,RowIndex,Element); };
00156 
00157     /**
00158       Allocation operator
00159     */
00160     Matrix<T>& operator = (const Matrix &A);
00161 
00162     /**
00163       Fills the Matrix with given value
00164     */
00165     void fill(const T& Val);
00166 
00167     /**
00168       Clears the Matrix (empty and size is 0)
00169     */
00170     void clear();
00171 
00172 };
00173 
00174 // =====================================================================
00175 // =====================================================================
00176 
00177 template <class T>
00178 Matrix<T>::Matrix():
00179   m_Data(boost::extents[0][0],boost::fortran_storage_order()),
00180   m_ColsNbr(0),m_RowsNbr(0)
00181 {
00182 }
00183 
00184 
00185 // =====================================================================
00186 // =====================================================================
00187 
00188 template <class T>
00189 Matrix<T>::Matrix(const Matrix &A):
00190   m_Data(boost::extents[A.m_ColsNbr][A.m_RowsNbr],boost::fortran_storage_order()),
00191   m_ColsNbr(A.m_ColsNbr),m_RowsNbr(A.m_RowsNbr)
00192 {
00193   m_Data = A.m_Data;
00194 }
00195 
00196 
00197 // =====================================================================
00198 // =====================================================================
00199 
00200 template <class T>
00201 Matrix<T>::Matrix(unsigned long ColsNbr, unsigned long RowsNbr) :
00202   m_Data(boost::extents[ColsNbr][RowsNbr],boost::fortran_storage_order()),
00203   m_ColsNbr(ColsNbr),m_RowsNbr(RowsNbr)
00204 {
00205   fill(0);
00206 }
00207 
00208 
00209 // =====================================================================
00210 // =====================================================================
00211 
00212 
00213 template <class T>
00214 Matrix<T>::Matrix(unsigned long ColsNbr, unsigned long RowsNbr, T InitValue) :
00215   m_Data(boost::extents[ColsNbr][RowsNbr],boost::fortran_storage_order()),
00216   m_ColsNbr(ColsNbr),m_RowsNbr(RowsNbr)
00217 {
00218   fill(InitValue);
00219 }
00220 
00221 
00222 // =====================================================================
00223 // =====================================================================
00224 
00225 
00226 template <class T>
00227 void Matrix<T>::setData(T* Data)
00228 {
00229   for (unsigned long j=0; j < m_RowsNbr;j++)
00230   {
00231     for (unsigned long i=0; i < m_ColsNbr;i++)
00232     {
00233       m_Data[i][j] = Data[i+(j*m_ColsNbr)];
00234     }
00235   }
00236 }
00237 
00238 
00239 // =====================================================================
00240 // =====================================================================
00241 
00242 
00243 template <class T>
00244 T Matrix<T>::getElement(unsigned long ColIndex, unsigned long RowIndex) const
00245 {
00246   if (ColIndex >= m_ColsNbr || RowIndex >= m_RowsNbr) throw openfluid::base::FrameworkException("Matrix::getElement","element access range error");
00247   return m_Data[ColIndex][RowIndex];
00248 }
00249 
00250 
00251 // =====================================================================
00252 // =====================================================================
00253 
00254 
00255 template <class T>
00256 void Matrix<T>::setElement(unsigned long ColIndex, unsigned long RowIndex, T Element)
00257 {
00258   if (ColIndex >= m_ColsNbr || RowIndex >= m_RowsNbr) throw openfluid::base::FrameworkException("Matrix::setElement","element access range error");
00259   m_Data[ColIndex][RowIndex] = Element;
00260 }
00261 
00262 
00263 
00264 // =====================================================================
00265 // =====================================================================
00266 
00267 template <class T>
00268 Matrix<T>& Matrix<T>::operator=(const Matrix &A)
00269 {
00270 
00271   if (this == &A) return *this; // in case somebody tries assign array to itself
00272 
00273   m_Data.resize(boost::extents[A.m_ColsNbr][A.m_RowsNbr]);
00274   m_Data = A.m_Data;
00275   m_ColsNbr = A.m_ColsNbr;
00276   m_RowsNbr = A.m_RowsNbr;
00277 
00278   return *this;
00279 }
00280 
00281 
00282 // =====================================================================
00283 // =====================================================================
00284 
00285 
00286 template <class T>
00287 void Matrix<T>::fill(const T& Val)
00288 {
00289   for (unsigned long i=0;i<m_ColsNbr;i++)
00290     for (unsigned long j=0;j<m_RowsNbr;j++)
00291       m_Data[i][j] = Val;
00292 }
00293 
00294 
00295 // =====================================================================
00296 // =====================================================================
00297 
00298 template <class T>
00299 void Matrix<T>::clear()
00300 {
00301   m_Data.resize(boost::extents[0][0]);
00302   m_ColsNbr=0;
00303   m_RowsNbr=0;
00304 }
00305 
00306 
00307 
00308 } }
00309 
00310 #endif /* __MATRIX_HPP___ */
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines