00001 /* 00002 00003 Copyright (C) University of Oxford, 2005-2010 00004 00005 University of Oxford means the Chancellor, Masters and Scholars of the 00006 University of Oxford, having an administrative office at Wellington 00007 Square, Oxford OX1 2JD, UK. 00008 00009 This file is part of Chaste. 00010 00011 Chaste is free software: you can redistribute it and/or modify it 00012 under the terms of the GNU Lesser General Public License as published 00013 by the Free Software Foundation, either version 2.1 of the License, or 00014 (at your option) any later version. 00015 00016 Chaste is distributed in the hope that it will be useful, but WITHOUT 00017 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 00018 FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public 00019 License for more details. The offer of Chaste under the terms of the 00020 License is subject to the License being interpreted in accordance with 00021 English Law and subject to any action against the University of Oxford 00022 being under the jurisdiction of the English Courts. 00023 00024 You should have received a copy of the GNU Lesser General Public License 00025 along with Chaste. If not, see <http://www.gnu.org/licenses/>. 00026 00027 */ 00028 00029 00030 #ifndef DISTRIBUTEDVECTOR_HPP_ 00031 #define DISTRIBUTEDVECTOR_HPP_ 00032 00033 #include <vector> 00034 #include <petscvec.h> 00035 #include <iostream> 00036 #include <cassert> 00037 00038 #include "DistributedVectorException.hpp" 00039 00040 class DistributedVectorFactory; 00041 00048 class DistributedVector 00049 { 00050 private: 00051 friend class TestDistributedVector; 00052 00053 // Data global to all vectors. 00054 00056 unsigned mLo; 00057 00059 unsigned mHi; 00060 00062 unsigned mProblemSize; 00063 00064 // Data local to a single vector. 00066 unsigned mSizeMultiplier; 00068 Vec mVec; 00070 double* mpVec; 00071 00076 DistributedVectorFactory* mpFactory; 00077 00078 public: 00079 00085 bool IsGlobalIndexLocal(unsigned globalIndex); 00086 00096 DistributedVector(Vec vec, DistributedVectorFactory* pFactory); 00097 00101 unsigned GetHigh() const 00102 { 00103 return mHi; 00104 } 00105 00109 unsigned GetLow() const 00110 { 00111 return mLo; 00112 } 00113 00117 DistributedVectorFactory* GetFactory() 00118 { 00119 return mpFactory; 00120 } 00121 00129 double& operator[](unsigned globalIndex) throw (DistributedVectorException); 00130 00136 void Restore(); 00137 00142 class Iterator 00143 { 00144 public: 00145 unsigned Local; 00146 unsigned Global; 00153 bool operator!=(const Iterator& rOther); 00154 00156 Iterator& operator++(); 00157 }; 00158 00166 class Stripe 00167 { 00168 unsigned mStride; 00169 unsigned mStripe; 00170 double* mpVec; 00171 unsigned mLo; 00172 unsigned mHi; 00173 DistributedVectorFactory* mpFactory; 00175 public: 00182 Stripe(DistributedVector parallelVec, unsigned stripe) 00183 { 00184 mStride = parallelVec.mSizeMultiplier; 00185 mStripe = stripe; 00186 assert(mStripe < mStride); 00187 mpVec = parallelVec.mpVec; 00188 mLo = parallelVec.GetLow(); 00189 mHi = parallelVec.GetHigh(); 00190 mpFactory = parallelVec.GetFactory(); 00191 } 00192 00196 DistributedVectorFactory* GetFactory() 00197 { 00198 return mpFactory; 00199 } 00200 00209 double& operator[](unsigned globalIndex) throw (DistributedVectorException) 00210 { 00211 if (mLo <= globalIndex && globalIndex < mHi) 00212 { 00213 return mpVec[(globalIndex - mLo)*mStride + mStripe]; 00214 } 00215 throw DistributedVectorException(); 00216 } 00217 00222 double& operator[](Iterator index) throw (DistributedVectorException) 00223 { 00224 return mpVec[index.Local*mStride + mStripe]; 00225 } 00226 00227 }; 00228 00236 class Chunk 00237 { 00238 unsigned mOffset; 00239 double* mpVec; 00240 unsigned mLo; 00241 unsigned mHi; 00243 public: 00250 Chunk(DistributedVector parallelVec, unsigned chunk) 00251 { 00252 assert(chunk < parallelVec.mSizeMultiplier); 00253 mLo = parallelVec.GetLow(); 00254 mHi = parallelVec.GetHigh(); 00255 mOffset = chunk * (mHi - mLo); 00256 mpVec = parallelVec.mpVec; 00257 } 00258 00267 double& operator[](unsigned globalIndex) throw (DistributedVectorException) 00268 { 00269 if (mLo <= globalIndex && globalIndex < mHi) 00270 { 00271 //localIndex = globalIndex - mLo 00272 return mpVec[mOffset + globalIndex - mLo]; 00273 } 00274 throw DistributedVectorException(); 00275 } 00276 00281 double& operator[](Iterator index) throw (DistributedVectorException) 00282 { 00283 return mpVec[mOffset + index.Local]; 00284 } 00285 00286 }; 00287 00292 Iterator Begin(); 00293 00298 Iterator End(); 00299 00305 double& operator[](Iterator index) throw (DistributedVectorException); 00306 }; 00307 00308 00309 00310 #endif /*DISTRIBUTEDVECTOR_HPP_*/