1 /* ***************************************************************** 2 MESQUITE -- The Mesh Quality Improvement Toolkit 3 4 Copyright 2004 Sandia Corporation and Argonne National 5 Laboratory. Under the terms of Contract DE-AC04-94AL85000 6 with Sandia Corporation, the U.S. Government retains certain 7 rights in this software. 8 9 This library is free software; you can redistribute it and/or 10 modify it under the terms of the GNU Lesser General Public 11 License as published by the Free Software Foundation; either 12 version 2.1 of the License, or (at your option) any later version. 13 14 This library is distributed in the hope that it will be useful, 15 but WITHOUT ANY WARRANTY; without even the implied warranty of 16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 17 Lesser General Public License for more details. 18 19 You should have received a copy of the GNU Lesser General Public License 20 (lgpl.txt) along with this library; if not, write to the Free Software 21 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 22 23 diachin2@llnl.gov, djmelan@sandia.gov, mbrewer@sandia.gov, 24 pknupp@sandia.gov, tleurent@mcs.anl.gov, tmunson@mcs.anl.gov 25 26 ***************************************************************** */ 27 // -*- Mode : c++; tab-width: 3; c-tab-always-indent: t; indent-tabs-mode: nil; c-basic-offset: 3 -*- 28 29 /*! \file LPtoPTemplate.hpp 30 \brief Header file for the MBMesquite::LPtoPTemplate class 31 \author Michael Brewer 32 \author Thomas Leurent 33 \date 2002-05-23 34 */ 35 36 37 #ifndef LPtoPTemplate_hpp 38 #define LPtoPTemplate_hpp 39 40 #include "Mesquite.hpp" 41 #include "ObjectiveFunctionTemplate.hpp" 42 43 namespace MBMesquite 44 { 45 class Matrix3D; 46 47 /*! \class LPtoPTemplate 48 \brief Calculates the L_p objective function raised to the pth 49 power. That is, sums the p_th powers of (the absolute value of) 50 the quality metric values. 51 52 \todo MB. Suggestions made by Todd Munson: 53 a) There is an inconsistent use of fabs. The hessian evaluation 54 when using the one norm does not take the absolute value, while the 55 gradient does. 56 b) The analytic gradient and hessian evaluations are incorrect when 57 the quality metric changes sign due to taking the absolute value. 58 The negative of the element gradient and hessian also needs to be 59 taken. 60 c) Done. The analytic gradient and hessian evaluations are 61 incorrect when the negate flag is set to -1. The negative 62 of the element gradient and hessian also needs to be taken 63 in this case. 64 d) The malloc in the concrete_eval routine should be removed. 65 66 */ 67 class LPtoPTemplate :public ObjectiveFunctionTemplate 68 { 69 public: 70 MESQUITE_EXPORT 71 LPtoPTemplate(QualityMetric *, short, MsqError &); 72 MESQUITE_EXPORT 73 LPtoPTemplate( short, QualityMetric* ); 74 75 MESQUITE_EXPORT 76 virtual ~LPtoPTemplate(); 77 78 MESQUITE_EXPORT 79 virtual void clear(); 80 81 MESQUITE_EXPORT 82 virtual bool evaluate( EvalType type, 83 PatchData& pd, 84 double& value_out, 85 bool free, 86 MsqError& err ); 87 88 MESQUITE_EXPORT 89 virtual bool evaluate_with_gradient( EvalType type, 90 PatchData& pd, 91 double& value_out, 92 std::vector<Vector3D>& grad_out, 93 MsqError& err ); 94 95 MESQUITE_EXPORT 96 virtual bool evaluate_with_Hessian_diagonal( EvalType type, 97 PatchData& pd, 98 double& value_out, 99 std::vector<Vector3D>& grad_out, 100 std::vector<SymMatrix3D>& hess_diag_out, 101 MsqError& err ); 102 103 MESQUITE_EXPORT 104 virtual bool evaluate_with_Hessian( EvalType type, 105 PatchData& pd, 106 double& value_out, 107 std::vector<Vector3D>& grad_out, 108 MsqHessian& Hessian_out, 109 MsqError& err ); 110 111 MESQUITE_EXPORT 112 virtual ObjectiveFunction* clone() const; 113 114 /*!Use set_dividing_by_n to control whether this objective 115 function divides it's final value by the number of 116 metric values used to compute the objective function 117 value. That is, if the associated metric is element 118 based, the obejctive function value is divided by 119 the number of elements. If it is vertex based, the 120 objective function is divided by the number of vertices. 121 If this function is passed 'true', the function value 122 will be scale. If it is passed false, the function 123 value will not be scaled.*/ 124 MESQUITE_EXPORT set_dividing_by_n(bool d_bool)125 void set_dividing_by_n(bool d_bool){dividingByN=d_bool;} 126 127 private: 128 double get_value( double power_sum, size_t count, EvalType type, 129 size_t& global_count, MsqError& err ); 130 131 //! The metric value entries are raised to the pVal power 132 short pVal; 133 //! dividingByN is true if we are dividing the objective function 134 //! by the number of metric values. 135 bool dividingByN; 136 137 138 size_t mCount; /**< The number of accumulated entires */ 139 double mPowSum; /**< The accumulated sum of values */ 140 size_t saveCount; /**< Saved count from previous patch */ 141 double savePowSum;/**< Saved sum from previous patch */ 142 143 /** Temporary storage for qm sample handles */ 144 mutable std::vector<size_t> qmHandles; 145 /** Temporary storage for qm vertex indices */ 146 mutable std::vector<size_t> mIndices; 147 /** Temporary storage for qm gradient */ 148 mutable std::vector<Vector3D> mGradient; 149 /** Temporary storage for qm Hessian diagonal blocks */ 150 mutable std::vector<SymMatrix3D> mDiag; 151 /** Temporary storage for qm Hessian */ 152 mutable std::vector<Matrix3D> mHessian; 153 }; 154 155 }//namespace 156 157 #endif // LPtoPTemplate_hpp 158 159