FEI Version of the Day
snl_fei_Constraint.hpp
00001 /*
00002 // @HEADER
00003 // ************************************************************************
00004 //             FEI: Finite Element Interface to Linear Solvers
00005 //                  Copyright (2005) Sandia Corporation.
00006 //
00007 // Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation, the
00008 // U.S. Government retains certain rights in this software.
00009 //
00010 // Redistribution and use in source and binary forms, with or without
00011 // modification, are permitted provided that the following conditions are
00012 // met:
00013 //
00014 // 1. Redistributions of source code must retain the above copyright
00015 // notice, this list of conditions and the following disclaimer.
00016 //
00017 // 2. Redistributions in binary form must reproduce the above copyright
00018 // notice, this list of conditions and the following disclaimer in the
00019 // documentation and/or other materials provided with the distribution.
00020 //
00021 // 3. Neither the name of the Corporation nor the names of the
00022 // contributors may be used to endorse or promote products derived from
00023 // this software without specific prior written permission.
00024 //
00025 // THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY
00026 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00027 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
00028 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE
00029 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
00030 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
00031 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
00032 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
00033 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
00034 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
00035 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00036 //
00037 // Questions? Contact Alan Williams (william@sandia.gov) 
00038 //
00039 // ************************************************************************
00040 // @HEADER
00041 */
00042 
00043 
00044 #ifndef _snl_fei_Constraint_hpp_
00045 #define _snl_fei_Constraint_hpp_
00046 
00047 #include <fei_macros.hpp>
00048 #include <fei_fwd.hpp>
00049 #include <fei_VectorSpace.hpp>
00050 #include <snl_fei_RecordCollection.hpp>
00051 
00052 #include <vector>
00053 
00054 namespace snl_fei {
00055 
00057   template<class RecordType>
00058   class Constraint {
00059   public:
00061     Constraint(int id=0, bool isPenaltyConstr=false);
00062 
00064     Constraint(int id,
00065                int constraintIDType,
00066                bool isSlave,
00067                bool isPenaltyConstr,
00068                int numIDs,
00069                const int* idTypes,
00070                const int* IDs,
00071                const int* fieldIDs,
00072                int offsetOfSlave,
00073                int offsetIntoSlaveField,
00074                const double* weights,
00075                double rhsValue,
00076                fei::VectorSpace* vspace);
00077 
00079     virtual ~Constraint();
00080 
00082     int getConstraintID() const { return( constraintID_ ); }
00083 
00085     void setConstraintID(int id) { constraintID_ = id; }
00086 
00088     int getIDType() const { return( idType_ ); }
00089 
00090     snl_fei::RecordCollection* getRecordCollection() { return recordCollection_; }
00091 
00094     void setIDType(int idType) { idType_ = idType; }
00095 
00097     bool isPenalty() const { return( isPenalty_ ); }
00098 
00101     void setIsPenalty(bool isPenaltyConstr) { isPenalty_ = isPenaltyConstr; }
00102 
00105     int getEqnNumber() const { return( eqnNumber_ ); }
00106 
00109     void setEqnNumber(int eqn) { eqnNumber_ = eqn; }
00110 
00113     int getBlkEqnNumber() const { return( blkEqnNumber_ ); }
00114 
00117     void setBlkEqnNumber(int blkEqn) { blkEqnNumber_ = blkEqn; }
00118 
00119 
00121     RecordType getSlave() { return getRecordCollection()->getRecordWithLocalID(slave_); }
00122 
00124     void setSlave(int slv) { slave_ = slv; }
00125 
00128     int getSlaveFieldID() const { return( slaveField_ ); }
00129 
00132     void setSlaveFieldID(int f) { slaveField_ = f; }
00133 
00135     int getOffsetIntoSlaveField() const { return( offsetIntoSlaveField_ ); }
00136 
00138     void setOffsetIntoSlaveField(int offset) { offsetIntoSlaveField_ = offset; }
00139 
00140 
00142     std::vector<int>& getMasters() { return( masters_ ); }
00143 
00145     std::vector<int>& getMasterIDTypes() { return( masterIDTypes_ ); }
00146 
00148     std::vector<snl_fei::RecordCollection*>& getMasterRecordCollections() { return masterRecordCollections_; }
00149 
00151     std::vector<int>& getMasterFieldIDs() { return( masterFields_ ); }
00152 
00154     std::vector<double>& getMasterWeights() { return( masterWeights_ ); }
00155 
00156 
00158     double getRHSValue() const { return( rhsValue_ ); }
00159 
00161     void setRHSValue(double rhs) { rhsValue_ = rhs; }
00162  
00164     bool operator!=(const Constraint<RecordType>& rhs);
00165 
00167     bool structurallySame(const Constraint<RecordType>& rhs);
00168 
00169   private:
00170     Constraint(const Constraint<RecordType>& src);
00171     Constraint<RecordType>& operator=(const Constraint<RecordType>& src);
00172 
00173     int constraintID_;
00174     int idType_;
00175     snl_fei::RecordCollection* recordCollection_;
00176     bool isPenalty_;
00177 
00178     int eqnNumber_;
00179     int blkEqnNumber_;
00180 
00181     int slave_;
00182     int slaveField_;
00183     int offsetIntoSlaveField_;
00184 
00185     std::vector<int> masters_;
00186     std::vector<int> masterIDTypes_;
00187     std::vector<snl_fei::RecordCollection*> masterRecordCollections_;
00188     std::vector<int> masterFields_;
00189     std::vector<double> masterWeights_;
00190 
00191     double rhsValue_;
00192 
00193   };//class Constraint
00194 } //namespace snl_fei
00195 
00196 #include <snl_fei_Constraint.hpp>
00197 
00198 //----------------------------------------------------------------------------
00199 template<class RecordType>
00200 inline snl_fei::Constraint<RecordType>::Constraint(int id, bool isPenaltyConstr)
00201   : constraintID_(id),
00202     idType_(0),
00203     recordCollection_(NULL),
00204     isPenalty_(isPenaltyConstr),
00205     eqnNumber_(-1),
00206     blkEqnNumber_(-1),
00207     slave_(),
00208     slaveField_(0),
00209     offsetIntoSlaveField_(0),
00210     masters_(),
00211     masterIDTypes_(),
00212     masterRecordCollections_(),
00213     masterFields_(),
00214     masterWeights_(),
00215     rhsValue_(0.0)
00216 {
00217 }
00218 
00219 //----------------------------------------------------------------------------
00220 template<class RecordType>
00221 inline snl_fei::Constraint<RecordType>::Constraint(int id,
00222                                             int constraintIDType,
00223                                             bool isSlave,
00224                                             bool isPenaltyConstr,
00225                                             int numIDs,
00226                                             const int* idTypes,
00227                                             const int* IDs,
00228                                             const int* fieldIDs,
00229                                             int offsetOfSlave,
00230                                             int offsetIntoSlaveField,
00231                                             const double* weights,
00232                                             double rhsValue,
00233                                             fei::VectorSpace* vspace)
00234   : constraintID_(id),
00235     idType_(constraintIDType),
00236     recordCollection_(NULL),
00237     isPenalty_(isPenaltyConstr),
00238     eqnNumber_(-1),
00239     blkEqnNumber_(-1), 
00240     slave_(),
00241     slaveField_(0),
00242     offsetIntoSlaveField_(offsetIntoSlaveField),
00243     masters_(),
00244     masterIDTypes_(),
00245     masterRecordCollections_(),
00246     masterFields_(),
00247     masterWeights_(),
00248     rhsValue_(rhsValue)
00249 {
00250 }
00251 
00252 //----------------------------------------------------------------------------
00253 namespace snl_fei {
00254 template<>
00255 inline snl_fei::Constraint<fei::Record<int>*>::Constraint(int id,
00256                                             int constraintIDType,
00257                                             bool isSlave,
00258                                             bool isPenaltyConstr,
00259                                             int numIDs,
00260                                             const int* idTypes,
00261                                             const int* IDs,
00262                                             const int* fieldIDs,
00263                                             int offsetOfSlave,
00264                                             int offsetIntoSlaveField,
00265                                             const double* weights,
00266                                             double rhsValue,
00267                                             fei::VectorSpace* vspace)
00268   : constraintID_(id),
00269     idType_(constraintIDType),
00270     recordCollection_(NULL),
00271     isPenalty_(isPenaltyConstr),
00272     eqnNumber_(-1),
00273     blkEqnNumber_(-1), 
00274     slave_(),
00275     slaveField_(0),
00276     offsetIntoSlaveField_(offsetIntoSlaveField),
00277     masters_(),
00278     masterIDTypes_(),
00279     masterRecordCollections_(),
00280     masterFields_(),
00281     masterWeights_(),
00282     rhsValue_(rhsValue)
00283 {
00284   int weightsOffset = 0;
00285   snl_fei::RecordCollection* recordCollection = NULL;
00286   vspace->getRecordCollection(idType_, recordCollection);
00287   recordCollection_ = recordCollection;
00288   for(int i=0; i<numIDs; ++i) {
00289     vspace->getRecordCollection(idTypes[i],recordCollection);
00290     masterRecordCollections_.push_back(recordCollection);
00291 
00292     vspace->addDOFs(fieldIDs[i], idTypes[i], 1, &(IDs[i]));
00293     int rec_local_id = recordCollection->getLocalID(IDs[i]);
00294     fei::Record<int>* rec = recordCollection->getRecordWithLocalID(rec_local_id);
00295     
00296     unsigned fieldSize = vspace->getFieldSize(fieldIDs[i]);
00297 
00298     if (isSlave && i == offsetOfSlave) {
00299       rec->hasSlaveDof(true);
00300       setSlave(rec_local_id);
00301       setSlaveFieldID(fieldIDs[i]);
00302       setOffsetIntoSlaveField(offsetIntoSlaveField);
00303       weightsOffset += fieldSize;
00304     }
00305     else {
00306       getMasters().push_back(rec_local_id);
00307       getMasterIDTypes().push_back(idTypes[i]);
00308       getMasterFieldIDs().push_back(fieldIDs[i]);
00309 
00310       if (weights != NULL) {
00311         for(unsigned j=0; j<fieldSize; ++j) {
00312           masterWeights_.push_back(weights[weightsOffset++]);
00313         }
00314       }
00315     }
00316   }
00317 }
00318 
00319 }//namespace snl_fei
00320 
00321 //----------------------------------------------------------------------------
00322 template<class RecordType>
00323 inline snl_fei::Constraint<RecordType>::Constraint(const Constraint<RecordType>& src)
00324   : constraintID_(-1),
00325     idType_(0),
00326     isPenalty_(false),
00327     eqnNumber_(-1),
00328     blkEqnNumber_(-1), 
00329     slave_(),
00330     slaveField_(0),
00331     offsetIntoSlaveField_(0),
00332     masters_(),
00333     masterIDTypes_(),
00334     masterRecordCollections_(),
00335     masterFields_(),
00336     masterWeights_(),
00337     rhsValue_(0.0)
00338 {
00339 }
00340 
00341 //----------------------------------------------------------------------------
00342 template<class RecordType>
00343 inline snl_fei::Constraint<RecordType>::~Constraint()
00344 {
00345 }
00346 
00347 //----------------------------------------------------------------------------
00348 template<class RecordType>
00349 inline bool snl_fei::Constraint<RecordType>::operator!=(const snl_fei::Constraint<RecordType>& rhs)
00350 {
00351   if (constraintID_ != rhs.constraintID_ ||
00352       idType_ != rhs.idType_ ||
00353       isPenalty_ != rhs.isPenalty_ ||
00354       eqnNumber_ != rhs.eqnNumber_ ||
00355       blkEqnNumber_ != rhs.blkEqnNumber_ ||
00356       slaveField_ != rhs.slaveField_ ||
00357       offsetIntoSlaveField_ != rhs.offsetIntoSlaveField_ ||
00358       rhsValue_ != rhs.rhsValue_) {
00359     return( true );
00360   }
00361 
00362   if (masters_ != rhs.masters_) return(true);
00363 
00364   if (masterIDTypes_ != rhs.masterIDTypes_) return(true);
00365 
00366   if (masterFields_ != rhs.masterFields_) return(true);
00367 
00368   if (masterWeights_ != rhs.masterWeights_) return(true);
00369 
00370   return(false);
00371 }
00372 
00373 //----------------------------------------------------------------------------
00374 template<class RecordType>
00375 inline bool snl_fei::Constraint<RecordType>::structurallySame(const Constraint<RecordType>& rhs)
00376 {
00377   if (constraintID_ != rhs.constraintID_ ||
00378       idType_ != rhs.idType_ ||
00379       isPenalty_ != rhs.isPenalty_ ||
00380       eqnNumber_ != rhs.eqnNumber_ ||
00381       blkEqnNumber_ != rhs.blkEqnNumber_ ||
00382       slaveField_ != rhs.slaveField_ ||
00383       offsetIntoSlaveField_ != rhs.offsetIntoSlaveField_) {
00384     return( false );
00385   }
00386 
00387   if (masters_ != rhs.masters_) return(false);
00388 
00389   if (masterIDTypes_ != rhs.masterIDTypes_) return(false);
00390 
00391   if (masterFields_ != rhs.masterFields_) return(false);
00392 
00393   return(true);
00394 }
00395 
00396 #endif // _snl_fei_Constraint_hpp_
00397 
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Friends