LCOV - code coverage report
Current view: top level - algs/AdvFront - AF2DfltRuleAppVisitor.cpp (source / functions) Hit Total Coverage
Test: coverage_sk.info Lines: 47 66 71.2 %
Date: 2020-07-01 15:24:36 Functions: 4 6 66.7 %
Branches: 14 40 35.0 %

           Branch data     Line data    Source code
       1                 :            : #include "meshkit/AF2DfltRuleAppVisitor.hpp"
       2                 :            : 
       3                 :            : // C++
       4                 :            : #include <cmath>
       5                 :            : #include <cstddef>
       6                 :            : 
       7                 :            : // MeshKit
       8                 :            : #include "meshkit/Error.hpp"
       9                 :            : 
      10                 :            : const double AF2DfltRuleAppVisitor::eqTriAreaPerimSqRatio = sqrt(3.0) / 36.0;
      11                 :            : 
      12                 :       9981 : AF2DfltRuleAppVisitor::AF2DfltRuleAppVisitor() :
      13                 :       9981 :     bestMetricVal(0), bestRuleApp(NULL)
      14                 :            : {
      15                 :       9981 : }
      16                 :            : 
      17                 :       9981 : AF2DfltRuleAppVisitor::~AF2DfltRuleAppVisitor()
      18                 :            : {
      19         [ +  + ]:       9981 :   if (bestRuleApp != NULL)
      20                 :            :   {
      21         [ +  - ]:       6543 :     delete bestRuleApp;
      22                 :            :   }
      23                 :       9981 : }
      24                 :            : 
      25                 :          0 : AF2DfltRuleAppVisitor::AF2DfltRuleAppVisitor(
      26                 :            :     const AF2DfltRuleAppVisitor & toCopy) :
      27                 :          0 :     bestMetricVal(toCopy.bestMetricVal)
      28                 :            : {
      29         [ #  # ]:          0 :   if (toCopy.bestRuleApp != NULL)
      30                 :            :   {
      31         [ #  # ]:          0 :     bestRuleApp = new AF2RuleApplication(*(toCopy.bestRuleApp));
      32                 :            :   }
      33                 :          0 : }
      34                 :            : 
      35                 :          0 : AF2DfltRuleAppVisitor& AF2DfltRuleAppVisitor::operator=(
      36                 :            :     const AF2DfltRuleAppVisitor & rhs)
      37                 :            : {
      38                 :          0 :   bestMetricVal = rhs.bestMetricVal;
      39                 :            : 
      40         [ #  # ]:          0 :   if (bestRuleApp == NULL)
      41                 :            :   {
      42         [ #  # ]:          0 :     if (rhs.bestRuleApp != NULL)
      43                 :            :     {
      44         [ #  # ]:          0 :       bestRuleApp = new AF2RuleApplication(*(rhs.bestRuleApp));
      45                 :            :     }
      46                 :            :   }
      47                 :            :   else
      48                 :            :   {
      49                 :          0 :     AF2RuleApplication* tempBestRuleApp = NULL;
      50         [ #  # ]:          0 :     if (rhs.bestRuleApp != NULL)
      51                 :            :     {
      52         [ #  # ]:          0 :       tempBestRuleApp = new AF2RuleApplication(*(rhs.bestRuleApp));
      53                 :            :     }
      54         [ #  # ]:          0 :     delete bestRuleApp;
      55                 :          0 :     bestRuleApp = tempBestRuleApp;
      56                 :            :   }
      57                 :            : 
      58                 :          0 :   return *this;
      59                 :            : }
      60                 :            : 
      61                 :       9981 : const AF2RuleApplication* AF2DfltRuleAppVisitor::getBestRuleApplication() const
      62                 :            : {
      63                 :       9981 :   return bestRuleApp;
      64                 :            : }
      65                 :            : 
      66                 :       7452 : void AF2DfltRuleAppVisitor::visit(AF2RuleApplication const & ruleApp)
      67                 :            : {
      68                 :       7452 :   double metricVal = 0.0;
      69                 :            : 
      70                 :            :   // loop over the faces and take the worst face metric value
      71                 :            :   // as the rule metric value
      72         [ +  + ]:      36986 :   for (unsigned int faceIndex = 0u;
      73                 :      18493 :       faceIndex < ruleApp.getNumNewFaces(); ++faceIndex)
      74                 :            :   {
      75                 :      11041 :     const AF2Polygon2D* facePtr = ruleApp.getNewFace(faceIndex);
      76                 :            : 
      77                 :            :     // verify that the face is a triangle
      78         [ -  + ]:      11041 :     if (facePtr->getNumVertices() != 3u)
      79                 :            :     {
      80         [ #  # ]:          0 :       MeshKit::Error badArg(MeshKit::MK_BAD_INPUT);
      81                 :            :       badArg.set_string(
      82         [ #  # ]:          0 :           "AF2DfltRuleAppVisitor can visit only triangular faces.");
      83         [ #  # ]:          0 :       throw badArg;
      84                 :            :     }
      85                 :            : 
      86                 :            :     // access the vertices of the triangle
      87                 :      11041 :     const AF2Point2D* faceVtx0 = facePtr->getVertex(0u);
      88                 :      11041 :     const AF2Point2D* faceVtx1 = facePtr->getVertex(1u);
      89                 :      11041 :     const AF2Point2D* faceVtx2 = facePtr->getVertex(2u);
      90                 :            : 
      91                 :            :     // calculate the components of the vectors along triangle edges
      92                 :      11041 :     double faceVec01X = faceVtx1->getX() - faceVtx0->getX();
      93                 :      11041 :     double faceVec01Y = faceVtx1->getY() - faceVtx0->getY();
      94                 :      11041 :     double faceVec02X = faceVtx2->getX() - faceVtx0->getX();
      95                 :      11041 :     double faceVec02Y = faceVtx2->getY() - faceVtx0->getY();
      96                 :      11041 :     double faceVec12X = faceVtx2->getX() - faceVtx1->getX();
      97                 :      11041 :     double faceVec12Y = faceVtx2->getY() - faceVtx1->getY();
      98                 :            : 
      99                 :            :     // calculate the length of each edge from the vector
     100                 :      11041 :     double sqLen = faceVec01X * faceVec01X + faceVec01Y * faceVec01Y;
     101                 :      11041 :     double faceVec01Len = sqrt(sqLen);
     102                 :      11041 :     sqLen = faceVec02X * faceVec02X + faceVec02Y * faceVec02Y;
     103                 :      11041 :     double faceVec02Len = sqrt(sqLen);
     104                 :      11041 :     sqLen = faceVec12X * faceVec12X + faceVec12Y * faceVec12Y;
     105                 :      11041 :     double faceVec12Len = sqrt(sqLen);
     106                 :            : 
     107                 :            :     // caculate the perimeter and area
     108                 :      11041 :     double facePerim = faceVec01Len + faceVec02Len + faceVec12Len;
     109                 :            :     double faceArea =
     110                 :      11041 :         0.5 * (faceVec01X * faceVec02Y - faceVec01Y * faceVec02X);
     111         [ -  + ]:      11041 :     if (faceArea <= 0.0)
     112                 :            :     {
     113                 :            :       // the face is inverted, so this rule application is unacceptable
     114                 :       7452 :       return;
     115                 :            :     }
     116                 :            : 
     117                 :            :     // calculate the face metric value
     118                 :      22082 :     double faceMetricVal = 10.0 * (eqTriAreaPerimSqRatio *
     119                 :      22082 :         facePerim * facePerim / faceArea - 1)  + // shape error
     120                 :      33123 :         1.0/faceVec01Len + faceVec01Len +
     121                 :      33123 :         1.0/faceVec02Len + faceVec02Len +
     122                 :      22082 :         1.0/faceVec12Len + faceVec12Len - 6.0; // size error
     123                 :            : 
     124                 :            :     // update the rule metric value, if necessary
     125         [ +  + ]:      11041 :     if (faceMetricVal > metricVal)
     126                 :            :     {
     127                 :       8570 :       metricVal = faceMetricVal;
     128                 :            :     }
     129                 :            :   }
     130                 :            : 
     131                 :            :   // update the best rule application if this is the only rule application
     132                 :            :   // or is a "measurable" improvement over the previous best
     133         [ +  + ]:       7452 :   if (bestRuleApp == NULL)
     134                 :            :   {
     135         [ +  - ]:       6543 :     bestRuleApp = new AF2RuleApplication(ruleApp);
     136                 :       6543 :     bestMetricVal = metricVal;
     137                 :            :   }
     138         [ +  + ]:        909 :   else if (metricVal < 0.99*bestMetricVal)
     139                 :            :   {
     140                 :        106 :     *bestRuleApp = ruleApp;
     141                 :        106 :     bestMetricVal = metricVal;
     142                 :            :   }
     143                 :            : }

Generated by: LCOV version 1.11