optimizerCommon.h

Go to the documentation of this file.
00001 
00015 #ifndef _DLR_OPTIMIZERCOMMON_H_
00016 #define _DLR_OPTIMIZERCOMMON_H_
00017 
00018 #include <cmath>
00019 #include <dlrNumeric/array2D.h>
00020 
00021 namespace dlr {
00022 
00023   namespace optimization {
00024 
00034     template <class ArgumentType>
00035     double
00036     contextSensitiveScale(const ArgumentType& vector,
00037                           const ArgumentType& point);
00038 
00039   
00048     template <class ArgumentType>
00049     inline void
00050     copyArgumentType(const ArgumentType& source, ArgumentType& target);
00051 
00052     
00064     template <class ArgumentType>
00065     double
00066     dotArgumentType(const ArgumentType& argument0,
00067                     const ArgumentType& argument1);
00068 
00069 
00083     template <class ArgumentType>
00084     void
00085     matrixMultiplyArgumentType(const Array2D<double>& matrix0,
00086                                const ArgumentType& vector0,
00087                                ArgumentType& result);
00088 
00089   } // namespace optimization
00090 
00091 } // namespace dlr
00092 
00093 
00094 /* ======= Declarations to maintain compatibility with legacy code. ======= */
00095 
00096 namespace dlr {
00097 
00098   using optimization::contextSensitiveScale;
00099   using optimization::copyArgumentType;
00100   using optimization::dotArgumentType;
00101   using optimization::matrixMultiplyArgumentType;
00102 
00103 } // namespace dlr
00104 
00105 
00106 /*******************************************************************
00107  * Function definitions follow.  This would be a .cpp file
00108  * if it weren't templated.
00109  *******************************************************************/
00110 
00111 #include <dlrCommon/exception.h>
00112 
00113 namespace dlr {
00114 
00115   namespace optimization {
00116 
00117     template <class ArgumentType>
00118     double
00119     contextSensitiveScale(const ArgumentType& vector,
00120                           const ArgumentType& point)
00121     {
00122       if(vector.size() != point.size()) {
00123         DLR_THROW3(ValueException, "contextSensitiveScale",
00124                    "Scaling arguments have different sizes.");
00125       }
00126       double chosenScale = 0.0;
00127       for(size_t index = 0; index < vector.size(); ++index) {
00128         double vectorElement = fabs(vector[index]);
00129         double pointElement = fabs(point[index]);
00130         if(pointElement < 1.0) {
00131           pointElement = 1.0;
00132         }
00133         double scaleCandidate = vectorElement / pointElement;
00134         if(scaleCandidate > chosenScale) {
00135           chosenScale = scaleCandidate;
00136         }
00137       }
00138       return chosenScale;
00139     }
00140 
00141 
00142 // This function copies an argument_type array in such a way that
00143 // the result is a deep copy of the original, even if argument_type
00144 // has shallow copy semantics.
00145     template <class ArgumentType>
00146     inline void
00147     copyArgumentType(const ArgumentType& source, ArgumentType& target) {
00148       if(target.size() != source.size()) {
00149         target = ArgumentType(source.size());
00150       }
00151       for(size_t index = 0; index < static_cast<size_t>(source.size());
00152           ++index) {
00153         target[index] = source[index];
00154       }
00155     }
00156 
00157     
00158 // This function computes the dot product of two ArgumentType instances.
00159     template <class ArgumentType>
00160     double
00161     dotArgumentType(const ArgumentType& argument0,
00162                     const ArgumentType& argument1)
00163     {
00164       // Make sure arguments are of the same size
00165       if(argument0.size() != argument1.size()) {
00166         DLR_THROW3(ValueException, "dotArgumentType()",
00167                    "Input arguments have different size.");
00168       }
00169       // Now compute the dot product.
00170       double result = 0.0;
00171       for(size_t index = 0; index < argument0.size(); ++index){
00172         result += argument0[index] * argument1[index];
00173       }
00174       return result;
00175     }
00176 
00177 // This function computes matrix product of an Array2D<double> instance
00178 // and an ArgumentType instance.
00179     template <class ArgumentType>
00180     void
00181     matrixMultiplyArgumentType(const Array2D<double>& matrix0,
00182                                const ArgumentType& vector0,
00183                                ArgumentType& result)
00184     {
00185       if(vector0.size() != matrix0.columns()) {
00186         std::ostringstream message;
00187         message << "Can't right-multiply a " << matrix0.rows() << " x "
00188                 << matrix0.columns() << " matrix by a " << vector0.size()
00189                 << " element vector.";
00190         DLR_THROW3(ValueException, "matrixMultiplyArgumentType(...)",
00191                    message.str().c_str());
00192       }
00193       if(result.size() != matrix0.rows()) {
00194         std::ostringstream message;
00195         message << "Matrix argument has " << matrix0.rows()
00196                 << " but result has " << result.size() << " elements.";
00197         DLR_THROW3(ValueException, "matrixMultiplyArgumentType(...)",
00198                    message.str().c_str());
00199       }
00200       for(size_t row = 0; row < matrix0.rows(); ++row) {
00201         result[row] = 0.0;
00202         for(size_t column = 0; column < matrix0.columns(); ++column) {
00203           result[row] += matrix0(row, column) * vector0[column];        
00204         }
00205       }
00206     }
00207 
00208   } // namespace optimization
00209 
00210 }; // namespace dlr
00211 
00212 #endif // #ifndef _DLR_OPTIMIZERCOMMON_H_

Generated on Mon Jul 9 20:34:03 2007 for dlrLibs Utility Libraries by  doxygen 1.5.2