OGS
Subdivision.cpp
Go to the documentation of this file.
1 
11 #include "Subdivision.h"
12 
13 #include <algorithm>
14 #include <cmath>
15 
16 #include "BaseLib/Error.h"
17 
18 namespace BaseLib
19 {
21  const double dL0,
22  const double max_dL,
23  const double multiplier)
24  : length_(L), dL0_(dL0), max_dL_(max_dL), multiplier_(multiplier)
25 {
26  // Check if accumulated subdivisions can ever sum up to length.
27  // Cf. geometric series formula.
28  if (multiplier < 1.0 && dL0 / (1.0 - multiplier) < L)
29  {
30  OGS_FATAL(
31  "Using dL0={:g} and multiplier={:g} the generated subdivisions can "
32  "not sum up to a total length of {:g}.",
33  dL0,
34  multiplier,
35  L);
36  }
37 }
38 
39 std::vector<double> GradualSubdivision::operator()() const
40 {
41  std::vector<double> vec_x;
42 
43  double x = 0;
44  unsigned i = 0;
45  do
46  {
47  vec_x.push_back(x);
48  x += std::min(max_dL_,
49  dL0_ * std::pow(multiplier_, static_cast<double>(i)));
50  i++;
51  } while (x < length_);
52 
53  if (vec_x.back() < length_)
54  {
55  double last_dx = vec_x[vec_x.size() - 1] - vec_x[vec_x.size() - 2];
56  if (length_ - vec_x.back() < last_dx)
57  {
58  vec_x[vec_x.size() - 1] = length_;
59  }
60  else
61  {
62  vec_x.push_back(length_);
63  }
64  }
65  return vec_x;
66 }
67 
69  const double L, const std::size_t num_subdivisions, const double multiplier)
70  : length_{L}, num_subdivisions_{num_subdivisions}, multiplier_{multiplier}
71 {
72 }
73 
74 std::vector<double> GradualSubdivisionFixedNum::operator()() const
75 {
76  std::vector<double> subdivisions;
77  subdivisions.reserve(num_subdivisions_ + 1);
78  subdivisions.push_back(0.0);
79  auto const q = multiplier_;
80 
81  if (q == 1.0)
82  {
83  double const dx = length_ / num_subdivisions_;
84 
85  for (std::size_t i = 1; i < num_subdivisions_; ++i)
86  {
87  subdivisions.push_back(dx * i);
88  }
89  }
90  else
91  {
92  // compute initial subdivision size
93  auto const a =
94  length_ * (q - 1.0) / (std::pow(q, num_subdivisions_) - 1.0);
95 
96  double qi = q; // q^i
97  for (std::size_t i = 1; i < num_subdivisions_; ++i)
98  {
99  subdivisions.push_back(a * (qi - 1.0) / (q - 1.0));
100  qi *= q;
101  }
102  }
103 
104  subdivisions.push_back(length_);
105 
106  return subdivisions;
107 }
108 
109 } // namespace BaseLib
#define OGS_FATAL(...)
Definition: Error.h:26
GradualSubdivisionFixedNum(const double L, const std::size_t num_subdivisions, const double multiplier)
Definition: Subdivision.cpp:68
std::vector< double > operator()() const override
Returns a vector of subdivided points.
Definition: Subdivision.cpp:74
GradualSubdivision(const double L, const double dL0, const double max_dL, const double multiplier)
Definition: Subdivision.cpp:20
std::vector< double > operator()() const override
Returns a vector of subdivided points.
Definition: Subdivision.cpp:39
static const double q