Intrepid
http://trilinos.sandia.gov/packages/docs/r10.12/packages/intrepid/test/Shared/FieldContainer/test_02.cpp
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 
00044 
00050 #include "Intrepid_FieldContainer.hpp"
00051 #include "Teuchos_oblackholestream.hpp"
00052 #include "Teuchos_RCP.hpp"
00053 #include "Teuchos_GlobalMPISession.hpp"
00054 
00055 
00056 using namespace Intrepid;
00057 
00058 int main(int argc, char *argv[]) {
00059 
00060   Teuchos::GlobalMPISession mpiSession(&argc, &argv);
00061   
00062   // This little trick lets us print to cout  only if a (dummy) command-line argument is provided.
00063   int iprint     = argc - 1;
00064   
00065   Teuchos::RCP<std::ostream> outStream;
00066   Teuchos::oblackholestream bhs; // outputs nothing
00067   
00068   if (iprint > 0)
00069     outStream = Teuchos::rcp(&std::cout, false);
00070   else
00071     outStream = Teuchos::rcp(&bhs, false);
00072   
00073   // Save the format state of the original cout .
00074   Teuchos::oblackholestream oldFormatState;
00075   oldFormatState.copyfmt(std::cout);
00076   
00077   *outStream  \
00078     << "===============================================================================\n" \
00079     << "|                                                                             |\n" \
00080     << "|                           Unit Test FieldContainer                          |\n" \
00081     << "|                                                                             |\n" \
00082     << "|     1) Testing exception handling                                           |\n" \
00083     << "|       requires intrepid to be configured with --enable-intrepid-debug       |\n" \
00084     << "|                                                                             |\n" \
00085     << "|  Questions? Contact  Pavel Bochev (pbboche@sandia.gov) or                   |\n" \
00086     << "|                      Denis Ridzal (dridzal@sandia.gov).                     |\n" \
00087     << "|                                                                             |\n" \
00088     << "|  Intrepid's website: http://trilinos.sandia.gov/packages/intrepid           |\n" \
00089     << "|  Trilinos website:   http://trilinos.sandia.gov                             |\n" \
00090     << "|                                                                             |\n" \
00091     << "===============================================================================\n";
00092   
00093   // Test initializations
00094   int errorFlag  = 0;
00095   
00096   // Define variables to create and use FieldContainers
00097   Teuchos::Array<int> dimensions;
00098   Teuchos::Array<int> multiIndex;
00099   
00100   // Initialize dimensions for rank-4 multi-index value
00101   dimensions.resize(4);
00102   dimensions[0] = 5;
00103   dimensions[1] = 3;
00104   dimensions[2] = 2;
00105   dimensions[3] = 7;
00106   
00107   // Create a FieldContainer
00108   FieldContainer<double> myContainer(dimensions);
00109   
00110   // These tests should only run if intrepid was configured with --enable-intrepid-debug option
00111   // Each test is designed to cause an exception. The total number of all caught exceptions should
00112   // be the same as the number of tests in this section.
00113 #ifdef HAVE_INTREPID_DEBUG
00114   
00115   *outStream << "\n" \
00116     << "===============================================================================\n"\
00117     << "| TEST 1: Catching exceptions                                                 |\n"\
00118     << "===============================================================================\n\n";
00119   
00120   int numTestException =16;
00121   int beginThrowNumber = Teuchos::TestForException_getThrowNumber();
00122   int endThrowNumber = beginThrowNumber + numTestException;
00123   
00124   try{ // Outer try block contains all tests for exception
00125     
00126     
00127     try{ // catch exception (1)
00128       
00129       //  Trying to  get enumeration using multi-index with the wrong rank:
00130       *outStream << "\n" \
00131       << "===============================================================================\n"\
00132       << "  Trying to  get enumeration using multi-index with the wrong rank: \n";
00133       multiIndex.resize(5);
00134       multiIndex[0] = 3; 
00135       multiIndex[1] = 1;
00136       multiIndex[2] = 2;
00137       multiIndex[3] = 2;
00138       multiIndex[4] = 6;
00139       myContainer.getEnumeration(multiIndex);
00140     }
00141     catch (std::logic_error err) {
00142       *outStream  << err.what() << "\n";
00143     };
00144     
00145     
00146     
00147     try{ // catch exception (2)
00148       
00149       // Trying to get enumeration using multi-index that is out of bounds: 3rd index is 4, must be <2
00150       *outStream << "\n" \
00151       << "===============================================================================\n"\
00152       << " Trying to get enumeration using multi-index that is out of bounds: \n";
00153       multiIndex.resize(4);
00154       multiIndex[0] = 3; 
00155       multiIndex[1] = 1;
00156       multiIndex[2] = 4;
00157       multiIndex[3] = 2;
00158       myContainer.getEnumeration(multiIndex);
00159     }
00160     catch (std::logic_error err) {
00161       *outStream  << err.what() << "\n";
00162     };
00163     
00164  
00165     
00166     try{  // catch exception (3)
00167       
00168       // Trying to set values from array whose size is less than FieldContainer's size:
00169       *outStream << "\n" \
00170       << "===============================================================================\n"\
00171       <<  " Trying to set values from array whose size is less than FieldContainer's size: \n";
00172       
00173       // Change one of the values of the dimensions to a lesser value: original value was 5 
00174       dimensions[0] = 4;
00175       
00176       // Define Teuchos::Array to store values with dimension equal to the number of multi-indexed values
00177       Teuchos::Array<double> dataTeuchosArray(4*3*2*7);
00178       
00179       // Fill with data
00180       int counter = 0;
00181       for(int i=0; i < dimensions[0]; i++){
00182         for(int j=0; j < dimensions[1]; j++){
00183           for(int k=0; k < dimensions[2]; k++){
00184             for(int l = 0; l < dimensions[3]; l++){
00185               dataTeuchosArray[counter] = (double)counter;
00186               counter++;
00187             }
00188           }
00189         }
00190       }
00191       
00192       // Now try to stuff this data into FieldContainer
00193       myContainer.setValues(dataTeuchosArray);
00194     }
00195     catch (std::logic_error err) {
00196       *outStream  << err.what() << "\n";
00197     };
00198     
00199     
00200     
00201     try{  // catch exception (4)
00202       
00203       // Trying to set values from array whose size is greater than FieldContainer's size:
00204       *outStream << "\n" \
00205       << "===============================================================================\n"\
00206       <<  " Trying to set values from array whose size is greater than FieldContainer's size: \n";
00207       
00208       // Change one of the values of the dimensions to a lesser value: restore dimensions[0] to the 
00209       // value used to construct the LexArray and change dimensions[2] to a greater value
00210       dimensions[0] = 5;
00211       dimensions[2] = 3;
00212       
00213       // Define Teuchos::Array to store values with dimension equal to the number of multi-indexed values
00214       Teuchos::ArrayRCP<double> dataTeuchosArray(5*3*3*7);
00215       
00216       // Fill with data
00217       int counter = 0;
00218       for(int i=0; i < dimensions[0]; i++){
00219         for(int j=0; j < dimensions[1]; j++){
00220           for(int k=0; k < dimensions[2]; k++){
00221             for(int l = 0; l < dimensions[3]; l++){
00222               dataTeuchosArray[counter] = (double)counter;
00223               counter++;
00224             }
00225           }
00226         }
00227       }
00228       
00229       // Now try to stuff this data into FieldContainer
00230       myContainer.setValues(dataTeuchosArray);
00231     }
00232     catch (std::logic_error err) {
00233       *outStream  << err.what() << "\n";
00234     };
00235     
00236     
00237     
00238     try{ // catch exception (5)
00239       
00240       // Trying to use [] with enumeration that is out of range:
00241       *outStream << "\n" \
00242       << "===============================================================================\n"\
00243       << " Trying to use [] with enumeration that is out of range: \n";
00244       myContainer[1000];
00245     }
00246     catch (std::logic_error err) {
00247       *outStream  << err.what() << "\n";
00248     }
00249     
00250     
00251     
00252     try{ // catch exception (6)
00253       
00254       // Trying to get multi-index from enumeration that is out of bounds:
00255       *outStream << "\n" \
00256       << "===============================================================================\n"\
00257       << " Trying to get multi-index from enumeration that is out of bounds: \n";
00258       myContainer.getMultiIndex(multiIndex,10000);
00259     }
00260     catch(std::logic_error err) {
00261      *outStream << err.what() << "\n";
00262     }
00263     
00264   
00265     
00266     try{ // catch exception (7)
00267       
00268       //Trying to self-assign FieldContainer
00269       *outStream << "\n" \
00270       << "===============================================================================\n"\
00271       << " Trying to self-assign FieldContainer \n";
00272       myContainer = myContainer;
00273     }
00274     catch(std::logic_error err) {
00275       *outStream << err.what() << "\n"; 
00276     }
00277 
00278     
00279     // Container of rank-1
00280     FieldContainer<double> rank1Container(3);
00281     
00282     // catch exception (8): method is for rank-2 container
00283     try{  
00284       *outStream << "\n" \
00285       << "===============================================================================\n"\
00286       << " using a method for rank-2 container \n";
00287       rank1Container.getEnumeration(1,1); 
00288     }
00289     catch(std::logic_error err){
00290       *outStream << err.what() << "\n";
00291     }
00292     
00293     // catch exception (9): method is for rank-3 container
00294     try{  
00295       *outStream << "\n" \
00296       << "===============================================================================\n"\
00297       << " using a method for rank-3 container \n";
00298       rank1Container.getEnumeration(1,1,1); 
00299     }
00300     catch(std::logic_error err){
00301       *outStream << err.what() << "\n";
00302     }
00303     
00304     // catch exception (10): method is for rank-4 container
00305     try{  
00306       *outStream << "\n" \
00307       << "===============================================================================\n"\
00308       << " using a method for rank-4 container \n";
00309       rank1Container.getEnumeration(1,1,1,1); 
00310     }
00311     catch(std::logic_error err){
00312       *outStream << err.what() << "\n";
00313     }
00314     
00315     // catch exception (11): method is for rank-5 container
00316     try{  
00317       *outStream << "\n" \
00318       << "===============================================================================\n"\
00319       << " using a method for rank-5 container \n";
00320       rank1Container.getEnumeration(1,1,1,1,1); 
00321     }
00322     catch(std::logic_error err){
00323       *outStream << err.what() << "\n";
00324     }
00325     
00326     // catch exception (12): 4 is out of bounds
00327     try{  
00328       *outStream << "\n" \
00329       << "===============================================================================\n"\
00330       << " The specified enumeration is out of bounds \n";
00331       int i0;
00332       rank1Container.getMultiIndex(i0,4); 
00333     }
00334     catch(std::logic_error err){
00335       *outStream << err.what() << "\n";
00336     }
00337     
00338     // catch exception (13): method for rank-2 container
00339     try{  
00340       *outStream << "\n" \
00341       << "===============================================================================\n"\
00342       << " Using a method for rank-2 containers \n";
00343       int i0,i1;
00344       rank1Container.getMultiIndex(i0,i1,2); 
00345     }
00346     catch(std::logic_error err){
00347       *outStream << err.what() << "\n";
00348     }
00349     
00350     // catch exception (14): method for rank-3 container
00351     try{  
00352       *outStream << "\n" \
00353       << "===============================================================================\n"\
00354       << " Using a method for rank-2 containers \n";
00355       int i0,i1,i2;
00356       rank1Container.getMultiIndex(i0,i1,i2,2); 
00357     }
00358     catch(std::logic_error err){
00359       *outStream << err.what() << "\n";
00360     }
00361     
00362     
00363     // catch exception (15): method for rank-4 container
00364     try{  
00365       *outStream << "\n" \
00366       << "===============================================================================\n"\
00367       << " Using a method for rank-4 containers \n";
00368       int i0,i1,i2,i3;
00369       rank1Container.getMultiIndex(i0,i1,i2,i3,2); 
00370     }
00371     catch(std::logic_error err){
00372       *outStream << err.what() << "\n";
00373     }
00374     
00375     
00376     // catch exception (16): method for rank-5 container
00377     try{  
00378       *outStream << "\n" \
00379       << "===============================================================================\n"\
00380       << " Using a method for rank-5 containers \n";
00381       int i0,i1,i2,i3,i4;
00382       rank1Container.getMultiIndex(i0,i1,i2,i3,i4,2); 
00383     }
00384     catch(std::logic_error err){
00385       *outStream << err.what() << "\n";
00386     }
00387     
00388     
00389     // Check if number of caught exceptions matches the expected number
00390     if (Teuchos::TestForException_getThrowNumber() != endThrowNumber) {
00391       errorFlag++;
00392       
00393     }
00394   } // outer try block
00395   catch (std::logic_error err) {
00396     *outStream << "UNEXPECTED ERROR !!! ----------------------------------------------------------\n";
00397     *outStream  << err.what() << "\n";
00398     *outStream << "-------------------------------------------------------------------------------" << "\n\n";
00399     errorFlag = -1000;
00400   }
00401 #endif
00402   
00403   if (errorFlag != 0)
00404     std::cout << "End Result: TEST FAILED\n";
00405   else
00406     std::cout << "End Result: TEST PASSED\n";
00407   
00408   // reset format state of std::cout
00409   std::cout.copyfmt(oldFormatState);
00410   
00411   return errorFlag;
00412 }