Intrepid
http://trilinos.sandia.gov/packages/docs/r10.12/packages/intrepid/src/Shared/Intrepid_ArrayToolsDefDot.hpp
Go to the documentation of this file.
00001 // @HEADER
00002 // ************************************************************************
00003 //
00004 //                           Intrepid Package
00005 //                 Copyright (2007) Sandia Corporation
00006 //
00007 // Under terms of Contract DE-AC04-94AL85000, there is a non-exclusive
00008 // license for use of this work by or on behalf of the U.S. Government.
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 Pavel Bochev  (pbboche@sandia.gov)
00038 //                    Denis Ridzal  (dridzal@sandia.gov), or
00039 //                    Kara Peterson (kjpeter@sandia.gov)
00040 //
00041 // ************************************************************************
00042 // @HEADER
00043 
00049 namespace Intrepid {
00050 
00051 template<class Scalar, class ArrayOutFields, class ArrayInData, class ArrayInFields>
00052 void ArrayTools::dotMultiplyDataField(ArrayOutFields &       outputFields,
00053                                       const ArrayInData &    inputData,
00054                                       const ArrayInFields &  inputFields) {
00055 
00056 #ifdef HAVE_INTREPID_DEBUG
00057   if (inputFields.rank() > inputData.rank()) {
00058     TEUCHOS_TEST_FOR_EXCEPTION( ((inputData.rank() < 2) || (inputData.rank() > 4)), std::invalid_argument,
00059                         ">>> ERROR (ArrayTools::dotMultiplyDataField): Input data container must have rank 2, 3 or 4.");
00060     TEUCHOS_TEST_FOR_EXCEPTION( (inputFields.rank() != inputData.rank()+1), std::invalid_argument,
00061                         ">>> ERROR (ArrayTools::dotMultiplyDataField): Input fields container must have rank one larger than the rank of the input data container.");
00062     TEUCHOS_TEST_FOR_EXCEPTION( (outputFields.rank() != 3), std::invalid_argument,
00063                         ">>> ERROR (ArrayTools::dotMultiplyDataField): Output fields container must have rank 3.");
00064     TEUCHOS_TEST_FOR_EXCEPTION( (inputFields.dimension(0) != inputData.dimension(0) ), std::invalid_argument,
00065                         ">>> ERROR (ArrayTools::dotMultiplyDataField): Zeroth dimensions (number of integration domains) of the fields and data input containers must agree!");
00066     TEUCHOS_TEST_FOR_EXCEPTION( ( (inputFields.dimension(2) != inputData.dimension(1)) && (inputData.dimension(1) != 1) ), std::invalid_argument,
00067                         ">>> ERROR (ArrayTools::dotMultiplyDataField): Second dimension of the fields input container and first dimension of data input container (number of integration points) must agree or first data dimension must be 1!");
00068     for (int i=2; i<inputData.rank(); i++) {
00069       std::string errmsg  = ">>> ERROR (ArrayTools::dotMultiplyDataField): Dimensions ";
00070       errmsg += (char)(48+i);
00071       errmsg += " and ";
00072       errmsg += (char)(48+i+1);
00073       errmsg += " of the input data and fields containers must agree!";
00074       TEUCHOS_TEST_FOR_EXCEPTION( (inputData.dimension(i) != inputFields.dimension(i+1)), std::invalid_argument, errmsg );
00075     }
00076     for (int i=0; i<outputFields.rank(); i++) {
00077       std::string errmsg  = ">>> ERROR (ArrayTools::dotMultiplyDataField): Dimensions ";
00078       errmsg += (char)(48+i);
00079       errmsg += " of the input and output fields containers must agree!";
00080       TEUCHOS_TEST_FOR_EXCEPTION( (inputFields.dimension(i) != outputFields.dimension(i)), std::invalid_argument, errmsg );
00081     }
00082   }
00083   else {
00084     TEUCHOS_TEST_FOR_EXCEPTION( ((inputData.rank() < 2) || (inputData.rank() > 4)), std::invalid_argument,
00085                         ">>> ERROR (ArrayTools::dotMultiplyDataField): Input data container must have rank 2, 3 or 4.");
00086     TEUCHOS_TEST_FOR_EXCEPTION( (inputFields.rank() != inputData.rank()), std::invalid_argument,
00087                         ">>> ERROR (ArrayTools::dotMultiplyDataField): The rank of fields input container must equal the rank of data input container.");
00088     TEUCHOS_TEST_FOR_EXCEPTION( (outputFields.rank() != 3), std::invalid_argument,
00089                         ">>> ERROR (ArrayTools::dotMultiplyDataField): Output fields container must have rank 3.");
00090     TEUCHOS_TEST_FOR_EXCEPTION( ( (inputFields.dimension(1) != inputData.dimension(1)) && (inputData.dimension(1) != 1) ), std::invalid_argument,
00091                         ">>> ERROR (ArrayTools::dotMultiplyDataField): First dimensions of the fields and data input containers (number of integration points) must agree or first data dimension must be 1!");
00092     TEUCHOS_TEST_FOR_EXCEPTION( (inputFields.dimension(0) != outputFields.dimension(1)), std::invalid_argument,
00093                         ">>> ERROR (ArrayTools::dotMultiplyDataField): Zeroth dimension of the fields input container and first dimension of the fields output container (number of fields) must agree!");
00094     TEUCHOS_TEST_FOR_EXCEPTION( (inputFields.dimension(1) != outputFields.dimension(2)), std::invalid_argument,
00095                         ">>> ERROR (ArrayTools::dotMultiplyDataField): First dimension of the fields input container and second dimension of the fields output container (number of integration points) must agree!");
00096     TEUCHOS_TEST_FOR_EXCEPTION( (outputFields.dimension(0) != inputData.dimension(0)), std::invalid_argument,
00097                         ">>> ERROR (ArrayTools::dotMultiplyDataField): Zeroth dimensions of the fields output and data input containers (number of integration domains) must agree!");
00098     for (int i=2; i<inputData.rank(); i++) {
00099       std::string errmsg  = ">>> ERROR (ArrayTools::dotMultiplyDataField): Dimensions ";
00100       errmsg += (char)(48+i);
00101       errmsg += " of the input data and fields containers must agree!";
00102       TEUCHOS_TEST_FOR_EXCEPTION( (inputData.dimension(i) != inputFields.dimension(i)), std::invalid_argument, errmsg );
00103     }
00104   }
00105 #endif
00106 
00107   // get sizes
00108   int invalRank      = inputFields.rank();
00109   int dataRank       = inputData.rank();
00110   int numCells       = outputFields.dimension(0);
00111   int numFields      = outputFields.dimension(1);
00112   int numPoints      = outputFields.dimension(2);
00113   int numDataPoints  = inputData.dimension(1);
00114   int dim1Tens       = 0;
00115   int dim2Tens       = 0;
00116   if (dataRank > 2) {
00117     dim1Tens = inputData.dimension(2);
00118     if (dataRank > 3) {
00119       dim2Tens = inputData.dimension(3);
00120     }
00121   }
00122 
00123   Scalar temp(0);
00124 
00125   if (invalRank == dataRank + 1) {
00126 
00127     if (numDataPoints != 1) { // nonconstant data
00128 
00129       switch(invalRank) {
00130         case 3: {
00131           for(int cl = 0; cl < numCells; cl++) {
00132             for(int bf = 0; bf < numFields; bf++) {
00133               for(int pt = 0; pt < numPoints; pt++) {
00134                 outputFields(cl, bf, pt) = inputData(cl, pt)*inputFields(cl, bf, pt);
00135               } // P-loop
00136             } // F-loop
00137           } // C-loop
00138         }// case 3
00139         break;
00140 
00141         case 4: {
00142           for(int cl = 0; cl < numCells; cl++) {
00143             for(int bf = 0; bf < numFields; bf++) {
00144               for(int pt = 0; pt < numPoints; pt++) {
00145                 temp = 0;
00146                 for( int iVec = 0; iVec < dim1Tens; iVec++) {
00147                   temp += inputData(cl, pt, iVec)*inputFields(cl, bf, pt, iVec);
00148                 } // D1-loop
00149                 outputFields(cl, bf, pt) = temp;
00150               } // P-loop
00151             } // F-loop
00152           } // C-loop
00153         }// case 4
00154         break;
00155 
00156         case 5: {
00157           for(int cl = 0; cl < numCells; cl++) {
00158             for(int bf = 0; bf < numFields; bf++) {
00159               for(int pt = 0; pt < numPoints; pt++) {
00160                 temp = 0;
00161                 for(int iTens2 = 0; iTens2 < dim2Tens; iTens2++) {
00162                   for( int iTens1 = 0; iTens1 < dim1Tens; iTens1++) {
00163                     temp += inputData(cl, pt, iTens1, iTens2)*inputFields(cl, bf, pt, iTens1, iTens2);
00164                   } // D1-loop
00165                 } // D2-loop
00166                 outputFields(cl, bf, pt) =  temp;
00167               } // P-loop
00168             } // F-loop
00169           } // C-loop
00170         }// case 5
00171         break;
00172 
00173         default:
00174               TEUCHOS_TEST_FOR_EXCEPTION( !( (invalRank == 3) || (invalRank == 4) || (invalRank == 5) ), std::invalid_argument,
00175                                   ">>> ERROR (ArrayTools::dotMultiplyDataField): This branch of the method is defined only for rank-3, 4 or 5 input fields containers.");
00176       }// invalRank
00177 
00178     }
00179     else { //constant data
00180 
00181       switch(invalRank) {
00182         case 3: {
00183           for(int cl = 0; cl < numCells; cl++) {
00184             for(int bf = 0; bf < numFields; bf++) {
00185               for(int pt = 0; pt < numPoints; pt++) {
00186                 outputFields(cl, bf, pt) = inputData(cl, 0)*inputFields(cl, bf, pt);
00187               } // P-loop
00188             } // F-loop
00189           } // C-loop
00190         }// case 3
00191         break;
00192 
00193         case 4: {
00194           for(int cl = 0; cl < numCells; cl++) {
00195             for(int bf = 0; bf < numFields; bf++) {
00196               for(int pt = 0; pt < numPoints; pt++) {
00197               temp = 0;
00198                 for( int iVec = 0; iVec < dim1Tens; iVec++) {
00199                   temp += inputData(cl, 0, iVec)*inputFields(cl, bf, pt, iVec);
00200                 } // D1-loop
00201                 outputFields(cl, bf, pt) = temp;
00202               } // P-loop
00203             } // F-loop
00204           } // C-loop
00205         }// case 4
00206         break;
00207 
00208         case 5: {
00209           for(int cl = 0; cl < numCells; cl++) {
00210             for(int bf = 0; bf < numFields; bf++) {
00211               for(int pt = 0; pt < numPoints; pt++) {
00212                 temp = 0;
00213                 for(int iTens2 = 0; iTens2 < dim2Tens; iTens2++) {
00214                   for( int iTens1 = 0; iTens1 < dim1Tens; iTens1++) {
00215                     temp += inputData(cl, 0, iTens1, iTens2)*inputFields(cl, bf, pt, iTens1, iTens2);
00216                   } // D1-loop
00217                 } // D2-loop
00218                 outputFields(cl, bf, pt) =  temp;
00219               } // P-loop
00220             } // F-loop
00221           } // C-loop
00222         }// case 5
00223         break;
00224 
00225         default:
00226               TEUCHOS_TEST_FOR_EXCEPTION( !( (invalRank == 3) || (invalRank == 4) || (invalRank == 5) ), std::invalid_argument,
00227                                   ">>> ERROR (ArrayTools::dotMultiplyDataField): This branch of the method is defined only for rank-3, 4 or 5 input fields containers.");
00228       }// invalRank
00229 
00230     } // numDataPoints
00231 
00232   }
00233   else {
00234 
00235     if (numDataPoints != 1) { // nonconstant data
00236 
00237       switch(invalRank) {
00238         case 2: {
00239           for(int cl = 0; cl < numCells; cl++) {
00240             for(int bf = 0; bf < numFields; bf++) {
00241               for(int pt = 0; pt < numPoints; pt++) {
00242                 outputFields(cl, bf, pt) = inputData(cl, pt)*inputFields(bf, pt);
00243               } // P-loop
00244             } // F-loop
00245           } // C-loop
00246         }// case 2
00247         break;
00248 
00249         case 3: {
00250           for(int cl = 0; cl < numCells; cl++) {
00251             for(int bf = 0; bf < numFields; bf++) {
00252               for(int pt = 0; pt < numPoints; pt++) {
00253                 temp = 0;
00254                 for( int iVec = 0; iVec < dim1Tens; iVec++) {
00255                   temp += inputData(cl, pt, iVec)*inputFields(bf, pt, iVec);
00256                 } // D1-loop
00257                 outputFields(cl, bf, pt) = temp;
00258               } // P-loop
00259             } // F-loop
00260           } // C-loop
00261         }// case 3
00262         break;
00263 
00264         case 4: {
00265           for(int cl = 0; cl < numCells; cl++) {
00266             for(int bf = 0; bf < numFields; bf++) {
00267               for(int pt = 0; pt < numPoints; pt++) {
00268                 temp = 0;
00269                 for(int iTens2 = 0; iTens2 < dim2Tens; iTens2++) {
00270                   for( int iTens1 = 0; iTens1 < dim1Tens; iTens1++) {
00271                     temp += inputData(cl, pt, iTens1, iTens2)*inputFields(bf, pt, iTens1, iTens2);
00272                   } // D1-loop
00273                 } // D2-loop
00274                 outputFields(cl, bf, pt) =  temp;
00275               } // P-loop
00276             } // F-loop
00277           } // C-loop
00278         }// case 4
00279         break;
00280 
00281         default:
00282               TEUCHOS_TEST_FOR_EXCEPTION( !( (invalRank == 2) || (invalRank == 3) || (invalRank == 4) ), std::invalid_argument,
00283                                   ">>> ERROR (ArrayTools::dotMultiplyDataField): This branch of the method is defined only for rank-2, 3 or 4 input fields containers.");
00284       }// invalRank
00285 
00286     }
00287     else { //constant data
00288 
00289       switch(invalRank) {
00290         case 2: {
00291           for(int cl = 0; cl < numCells; cl++) {
00292             for(int bf = 0; bf < numFields; bf++) {
00293               for(int pt = 0; pt < numPoints; pt++) {
00294                 outputFields(cl, bf, pt) = inputData(cl, 0)*inputFields(bf, pt);
00295               } // P-loop
00296             } // F-loop
00297           } // C-loop
00298         }// case 2
00299         break;
00300 
00301         case 3: {
00302           for(int cl = 0; cl < numCells; cl++) {
00303             for(int bf = 0; bf < numFields; bf++) {
00304               for(int pt = 0; pt < numPoints; pt++) {
00305               temp = 0;
00306                 for( int iVec = 0; iVec < dim1Tens; iVec++) {
00307                   temp += inputData(cl, 0, iVec)*inputFields(bf, pt, iVec);
00308                 } // D1-loop
00309                 outputFields(cl, bf, pt) = temp;
00310               } // P-loop
00311             } // F-loop
00312           } // C-loop
00313         }// case 3
00314         break;
00315 
00316         case 4: {
00317           for(int cl = 0; cl < numCells; cl++) {
00318             for(int bf = 0; bf < numFields; bf++) {
00319               for(int pt = 0; pt < numPoints; pt++) {
00320                 temp = 0;
00321                 for(int iTens2 = 0; iTens2 < dim2Tens; iTens2++) {
00322                   for( int iTens1 = 0; iTens1 < dim1Tens; iTens1++) {
00323                     temp += inputData(cl, 0, iTens1, iTens2)*inputFields(bf, pt, iTens1, iTens2);
00324                   } // D1-loop
00325                 } // D2-loop
00326                 outputFields(cl, bf, pt) =  temp;
00327               } // P-loop
00328             } // F-loop
00329           } // C-loop
00330         }// case 4
00331         break;
00332 
00333         default:
00334               TEUCHOS_TEST_FOR_EXCEPTION( !( (invalRank == 2) || (invalRank == 3) || (invalRank == 4) ), std::invalid_argument,
00335                                   ">>> ERROR (ArrayTools::dotMultiplyDataField): This branch of the method is defined only for rank-2, 3 or 4 input fields containers.");
00336       }// invalRank
00337 
00338     } // numDataPoints
00339 
00340   } // end if (invalRank == dataRank + 1)
00341 
00342 }// dotMultiplyDataField
00343 
00344 
00345 
00346 template<class Scalar, class ArrayOutData, class ArrayInDataLeft, class ArrayInDataRight>
00347 void ArrayTools::dotMultiplyDataData(ArrayOutData &            outputData,
00348                                      const ArrayInDataLeft  &  inputDataLeft,
00349                                      const ArrayInDataRight &  inputDataRight) {
00350 
00351 #ifdef HAVE_INTREPID_DEBUG
00352   if (inputDataRight.rank() >= inputDataLeft.rank()) {
00353     TEUCHOS_TEST_FOR_EXCEPTION( ((inputDataLeft.rank() < 2) || (inputDataLeft.rank() > 4)), std::invalid_argument,
00354                         ">>> ERROR (ArrayTools::dotMultiplyDataData): Left data input container must have rank 2, 3 or 4.");
00355     TEUCHOS_TEST_FOR_EXCEPTION( (inputDataRight.rank() != inputDataLeft.rank()), std::invalid_argument,
00356                         ">>> ERROR (ArrayTools::dotMultiplyDataData): The rank of the right data input container must equal the rank of the left data input container.");
00357     TEUCHOS_TEST_FOR_EXCEPTION( (outputData.rank() != 2), std::invalid_argument,
00358                         ">>> ERROR (ArrayTools::dotMultiplyDataData): Data output container must have rank 2.");
00359     TEUCHOS_TEST_FOR_EXCEPTION( ( (inputDataRight.dimension(1) != inputDataLeft.dimension(1)) && (inputDataLeft.dimension(1) != 1) ), std::invalid_argument,
00360                         ">>> ERROR (ArrayTools::dotMultiplyDataField): First dimensions of the left and right data input containers (number of integration points) must agree or first left data dimension must be 1!");
00361     for (int i=0; i<inputDataLeft.rank(); i++) {
00362       if (i != 1) {
00363         std::string errmsg  = ">>> ERROR (ArrayTools::dotMultiplyDataData): Dimensions ";
00364         errmsg += (char)(48+i);
00365         errmsg += " of the left and right data input containers must agree!";
00366         TEUCHOS_TEST_FOR_EXCEPTION( (inputDataLeft.dimension(i) != inputDataRight.dimension(i)), std::invalid_argument, errmsg );
00367       }
00368     }
00369     for (int i=0; i<outputData.rank(); i++) {
00370       std::string errmsg  = ">>> ERROR (ArrayTools::dotMultiplyDataData): Dimensions ";
00371       errmsg += (char)(48+i);
00372       errmsg += " of the output and right input data containers must agree!";
00373       TEUCHOS_TEST_FOR_EXCEPTION( (inputDataRight.dimension(i) != outputData.dimension(i)), std::invalid_argument, errmsg );
00374     }
00375   }
00376   else {
00377     TEUCHOS_TEST_FOR_EXCEPTION( ((inputDataLeft.rank() < 2) || (inputDataLeft.rank() > 4)), std::invalid_argument,
00378                         ">>> ERROR (ArrayTools::dotMultiplyDataData): Left data input container must have rank 2, 3 or 4.");
00379     TEUCHOS_TEST_FOR_EXCEPTION( (inputDataRight.rank() != inputDataLeft.rank()-1), std::invalid_argument,
00380                         ">>> ERROR (ArrayTools::dotMultiplyDataData): Right data input container must have rank one less than the rank of left data input container.");
00381     TEUCHOS_TEST_FOR_EXCEPTION( (outputData.rank() != 2), std::invalid_argument,
00382                         ">>> ERROR (ArrayTools::dotMultiplyDataData): Data output container must have rank 2.");
00383     TEUCHOS_TEST_FOR_EXCEPTION( ( (inputDataRight.dimension(0) != inputDataLeft.dimension(1)) && (inputDataLeft.dimension(1) != 1) ), std::invalid_argument,
00384                         ">>> ERROR (ArrayTools::dotMultiplyDataField): Zeroth dimension of the right data input container and first dimension of left data input container (number of integration points) must agree or first left data dimension must be 1!");
00385     TEUCHOS_TEST_FOR_EXCEPTION( (inputDataRight.dimension(0) != outputData.dimension(1)), std::invalid_argument,
00386                         ">>> ERROR (ArrayTools::dotMultiplyDataField): Zeroth dimension of the right data input container and first dimension of output data container (number of integration points) must agree!");
00387     TEUCHOS_TEST_FOR_EXCEPTION( (inputDataLeft.dimension(0) != outputData.dimension(0)), std::invalid_argument,
00388                         ">>> ERROR (ArrayTools::dotMultiplyDataField): Zeroth dimensions of the left data input and data output containers (number of integration domains) must agree!");
00389     for (int i=1; i<inputDataRight.rank(); i++) {
00390       std::string errmsg  = ">>> ERROR (ArrayTools::dotMultiplyDataData): Dimensions ";
00391       errmsg += (char)(48+i+1);
00392       errmsg += " and ";
00393       errmsg += (char)(48+i);
00394       errmsg += " of the left and right data input containers must agree!";
00395       TEUCHOS_TEST_FOR_EXCEPTION( (inputDataLeft.dimension(i+1) != inputDataRight.dimension(i)), std::invalid_argument, errmsg );
00396     }
00397   }
00398 #endif
00399 
00400   // get sizes
00401   int rightDataRank  = inputDataRight.rank();
00402   int leftDataRank   = inputDataLeft.rank();
00403   int numCells       = outputData.dimension(0);
00404   int numPoints      = outputData.dimension(1);
00405   int numDataPoints  = inputDataLeft.dimension(1);
00406   int dim1Tens       = 0;
00407   int dim2Tens       = 0;
00408   if (leftDataRank > 2) {
00409     dim1Tens = inputDataLeft.dimension(2);
00410     if (leftDataRank > 3) {
00411       dim2Tens = inputDataLeft.dimension(3);
00412     }
00413   }
00414 
00415   Scalar temp(0);
00416 
00417   if (rightDataRank == leftDataRank) {
00418 
00419     if (numDataPoints != 1) { // nonconstant data
00420 
00421       switch(rightDataRank) {
00422         case 2: {
00423           for(int cl = 0; cl < numCells; cl++) {
00424             for(int pt = 0; pt < numPoints; pt++) {
00425                 outputData(cl, pt) = inputDataLeft(cl, pt)*inputDataRight(cl, pt);
00426             } // P-loop
00427           } // C-loop
00428         }// case 2
00429         break;
00430 
00431         case 3: {
00432           for(int cl = 0; cl < numCells; cl++) {
00433             for(int pt = 0; pt < numPoints; pt++) {
00434               temp = 0;
00435               for( int iVec = 0; iVec < dim1Tens; iVec++) {
00436                   temp += inputDataLeft(cl, pt, iVec)*inputDataRight(cl, pt, iVec);
00437               } // D1-loop
00438               outputData(cl, pt) = temp;
00439             } // P-loop
00440           } // C-loop
00441         }// case 3
00442         break;
00443 
00444         case 4: {
00445           for(int cl = 0; cl < numCells; cl++) {
00446             for(int pt = 0; pt < numPoints; pt++) {
00447               temp = 0;
00448               for(int iTens2 = 0; iTens2 < dim2Tens; iTens2++) {
00449                 for( int iTens1 = 0; iTens1 < dim1Tens; iTens1++) {
00450                     temp += inputDataLeft(cl, pt, iTens1, iTens2)*inputDataRight(cl, pt, iTens1, iTens2);
00451                 } // D1-loop
00452               } // D2-loop
00453               outputData(cl, pt) =  temp;
00454             } // P-loop
00455           } // C-loop
00456         }// case 4
00457         break;
00458 
00459         default:
00460               TEUCHOS_TEST_FOR_EXCEPTION( !( (rightDataRank == 2) || (rightDataRank == 3) || (rightDataRank == 4) ), std::invalid_argument,
00461                                   ">>> ERROR (ArrayTools::dotMultiplyDataData): This branch of the method is defined only for rank-2, 3 or 4 right data input containers.");
00462       }// rightDataRank
00463 
00464     }
00465     else { //constant data
00466 
00467       switch(rightDataRank) {
00468         case 2: {
00469           for(int cl = 0; cl < numCells; cl++) {
00470             for(int pt = 0; pt < numPoints; pt++) {
00471                 outputData(cl, pt) = inputDataLeft(cl, 0)*inputDataRight(cl, pt);
00472             } // P-loop
00473           } // C-loop
00474         }// case 2
00475         break;
00476 
00477         case 3: {
00478           for(int cl = 0; cl < numCells; cl++) {
00479             for(int pt = 0; pt < numPoints; pt++) {
00480               temp = 0;
00481               for( int iVec = 0; iVec < dim1Tens; iVec++) {
00482                   temp += inputDataLeft(cl, 0, iVec)*inputDataRight(cl, pt, iVec);
00483               } // D1-loop
00484               outputData(cl, pt) = temp;
00485             } // P-loop
00486           } // C-loop
00487         }// case 3
00488         break;
00489 
00490         case 4: {
00491           for(int cl = 0; cl < numCells; cl++) {
00492             for(int pt = 0; pt < numPoints; pt++) {
00493               temp = 0;
00494               for(int iTens2 = 0; iTens2 < dim2Tens; iTens2++) {
00495                 for( int iTens1 = 0; iTens1 < dim1Tens; iTens1++) {
00496                     temp += inputDataLeft(cl, 0, iTens1, iTens2)*inputDataRight(cl, pt, iTens1, iTens2);
00497                 } // D1-loop
00498               } // D2-loop
00499               outputData(cl, pt) =  temp;
00500             } // P-loop
00501           } // C-loop
00502         }// case 4
00503         break;
00504 
00505         default:
00506               TEUCHOS_TEST_FOR_EXCEPTION( !( (rightDataRank == 2) || (rightDataRank == 3) || (rightDataRank == 4) ), std::invalid_argument,
00507                                   ">>> ERROR (ArrayTools::dotMultiplyDataData): This branch of the method is defined only for rank-2, 3 or 4 right data input containers.");
00508       }// rightDataRank
00509 
00510     } // numDataPoints
00511 
00512   }
00513   else {
00514 
00515     if (numDataPoints != 1) { // nonconstant data
00516 
00517       switch(rightDataRank) {
00518         case 1: {
00519           for(int cl = 0; cl < numCells; cl++) {
00520             for(int pt = 0; pt < numPoints; pt++) {
00521                 outputData(cl, pt) = inputDataLeft(cl, pt)*inputDataRight(pt);
00522             } // P-loop
00523           } // C-loop
00524         }// case 1
00525         break;
00526 
00527         case 2: {
00528           for(int cl = 0; cl < numCells; cl++) {
00529             for(int pt = 0; pt < numPoints; pt++) {
00530               temp = 0;
00531               for( int iVec = 0; iVec < dim1Tens; iVec++) {
00532                   temp += inputDataLeft(cl, pt, iVec)*inputDataRight(pt, iVec);
00533               } // D1-loop
00534               outputData(cl, pt) = temp;
00535             } // P-loop
00536           } // C-loop
00537         }// case 2
00538         break;
00539 
00540         case 3: {
00541           for(int cl = 0; cl < numCells; cl++) {
00542             for(int pt = 0; pt < numPoints; pt++) {
00543               temp = 0;
00544               for(int iTens2 = 0; iTens2 < dim2Tens; iTens2++) {
00545                 for( int iTens1 = 0; iTens1 < dim1Tens; iTens1++) {
00546                     temp += inputDataLeft(cl, pt, iTens1, iTens2)*inputDataRight(pt, iTens1, iTens2);
00547                 } // D1-loop
00548               } // D2-loop
00549               outputData(cl, pt) =  temp;
00550             } // P-loop
00551           } // C-loop
00552         }// case 3
00553         break;
00554 
00555         default:
00556               TEUCHOS_TEST_FOR_EXCEPTION( !( (rightDataRank == 1) || (rightDataRank == 2) || (rightDataRank == 3) ), std::invalid_argument,
00557                                   ">>> ERROR (ArrayTools::dotMultiplyDataData): This branch of the method is defined only for rank-1, 2 or 3 right data input containers.");
00558       }// rightDataRank
00559 
00560     }
00561     else { //constant data
00562 
00563       switch(rightDataRank) {
00564         case 1: {
00565           for(int cl = 0; cl < numCells; cl++) {
00566             for(int pt = 0; pt < numPoints; pt++) {
00567                 outputData(cl, pt) = inputDataLeft(cl, 0)*inputDataRight(pt);
00568             } // P-loop
00569           } // C-loop
00570         }// case 1
00571         break;
00572 
00573         case 2: {
00574           for(int cl = 0; cl < numCells; cl++) {
00575             for(int pt = 0; pt < numPoints; pt++) {
00576               temp = 0;
00577               for( int iVec = 0; iVec < dim1Tens; iVec++) {
00578                   temp += inputDataLeft(cl, 0, iVec)*inputDataRight(pt, iVec);
00579               } // D1-loop
00580               outputData(cl, pt) = temp;
00581             } // P-loop
00582           } // C-loop
00583         }// case 2
00584         break;
00585 
00586         case 3: {
00587           for(int cl = 0; cl < numCells; cl++) {
00588             for(int pt = 0; pt < numPoints; pt++) {
00589               temp = 0;
00590               for(int iTens2 = 0; iTens2 < dim2Tens; iTens2++) {
00591                 for( int iTens1 = 0; iTens1 < dim1Tens; iTens1++) {
00592                     temp += inputDataLeft(cl, 0, iTens1, iTens2)*inputDataRight(pt, iTens1, iTens2);
00593                 } // D1-loop
00594               } // D2-loop
00595               outputData(cl, pt) =  temp;
00596             } // P-loop
00597           } // C-loop
00598         }// case 3
00599         break;
00600 
00601         default:
00602               TEUCHOS_TEST_FOR_EXCEPTION( !( (rightDataRank == 1) || (rightDataRank == 2) || (rightDataRank == 3) ), std::invalid_argument,
00603                                   ">>> ERROR (ArrayTools::dotMultiplyDataData): This branch of the method is defined only for rank-1, 2 or 3 right data input containers.");
00604       }// rightDataRank
00605 
00606     } // numDataPoints
00607 
00608   } // end if (rightDataRank == leftDataRank)
00609 
00610 }// dotMultiplyDataData
00611 
00612 
00613 
00614 } // end namespace Intrepid