TheAlgorithms/C++ 1.0.0
All the algorithms implemented in C++
Loading...
Searching...
No Matches
composite_simpson_rule.cpp
Go to the documentation of this file.
1
38#include <cassert>
39#include <cmath>
40#include <cmath>
41#include <cstdint>
42#include <cstdlib>
43#include <functional>
44#include <iostream>
45#include <map>
46
51namespace numerical_methods {
56namespace simpson_method {
67double evaluate_by_simpson(std::int32_t N, double h, double a,
68 const std::function<double(double)>& func) {
69 std::map<std::int32_t, double>
70 data_table; // Contains the data points. key: i, value: f(xi)
71 double xi = a; // Initialize xi to the starting point x0 = a
72
73 // Create the data table
74 double temp = NAN;
75 for (std::int32_t i = 0; i <= N; i++) {
76 temp = func(xi);
77 data_table.insert(
78 std::pair<std::int32_t, double>(i, temp)); // add i and f(xi)
79 xi += h; // Get the next point xi for the next iteration
80 }
81
82 // Evaluate the integral.
83 // Remember: f(x0) + 4*f(x1) + 2*f(x2) + ... + 2*f(xN-2) + 4*f(xN-1) + f(xN)
84 double evaluate_integral = 0;
85 for (std::int32_t i = 0; i <= N; i++) {
86 if (i == 0 || i == N) {
87 evaluate_integral += data_table.at(i);
88 } else if (i % 2 == 1) {
89 evaluate_integral += 4 * data_table.at(i);
90 } else {
91 evaluate_integral += 2 * data_table.at(i);
92 }
93 }
94
95 // Multiply by the coefficient h/3
96 evaluate_integral *= h / 3;
97
98 // If the result calculated is nan, then the user has given wrong input
99 // interval.
100 assert(!std::isnan(evaluate_integral) &&
101 "The definite integral can't be evaluated. Check the validity of "
102 "your input.\n");
103 // Else return
104 return evaluate_integral;
105}
106
113double f(double x) { return std::sqrt(x) + std::log(x); }
115double g(double x) { return std::exp(-x) * (4 - std::pow(x, 2)); }
117double k(double x) { return std::sqrt(2 * std::pow(x, 3) + 3); }
119double l(double x) { return x + std::log(2 * x + 1); }
120} // namespace simpson_method
121} // namespace numerical_methods
122
132static void test(std::int32_t N, double h, double a, double b,
133 bool used_argv_parameters) {
134 // Call the functions and find the integral of each function
135 double result_f = numerical_methods::simpson_method::evaluate_by_simpson(
136 N, h, a, numerical_methods::simpson_method::f);
137 assert((used_argv_parameters || (result_f >= 4.09 && result_f <= 4.10)) &&
138 "The result of f(x) is wrong");
139 std::cout << "The result of integral f(x) on interval [" << a << ", " << b
140 << "] is equal to: " << result_f << std::endl;
141
142 double result_g = numerical_methods::simpson_method::evaluate_by_simpson(
143 N, h, a, numerical_methods::simpson_method::g);
144 assert((used_argv_parameters || (result_g >= 0.27 && result_g <= 0.28)) &&
145 "The result of g(x) is wrong");
146 std::cout << "The result of integral g(x) on interval [" << a << ", " << b
147 << "] is equal to: " << result_g << std::endl;
148
149 double result_k = numerical_methods::simpson_method::evaluate_by_simpson(
150 N, h, a, numerical_methods::simpson_method::k);
151 assert((used_argv_parameters || (result_k >= 9.06 && result_k <= 9.07)) &&
152 "The result of k(x) is wrong");
153 std::cout << "The result of integral k(x) on interval [" << a << ", " << b
154 << "] is equal to: " << result_k << std::endl;
155
156 double result_l = numerical_methods::simpson_method::evaluate_by_simpson(
157 N, h, a, numerical_methods::simpson_method::l);
158 assert((used_argv_parameters || (result_l >= 7.16 && result_l <= 7.17)) &&
159 "The result of l(x) is wrong");
160 std::cout << "The result of integral l(x) on interval [" << a << ", " << b
161 << "] is equal to: " << result_l << std::endl;
162}
163
170int main(int argc, char** argv) {
171 std::int32_t N = 16;
173 double a = 1, b = 3;
175 double h = NAN;
176
177 bool used_argv_parameters =
178 false; // If argv parameters are used then the assert must be omitted
179 // for the tst cases
180
181 // Get user input (by the command line parameters or the console after
182 // displaying messages)
183 if (argc == 4) {
184 N = std::atoi(argv[1]);
185 a = std::atof(argv[2]);
186 b = std::atof(argv[3]);
187 // Check if a<b else abort
188 assert(a < b && "a has to be less than b");
189 assert(N > 0 && "N has to be > 0");
190 if (N < 16 || a != 1 || b != 3) {
191 used_argv_parameters = true;
192 }
193 std::cout << "You selected N=" << N << ", a=" << a << ", b=" << b
194 << std::endl;
195 } else {
196 std::cout << "Default N=" << N << ", a=" << a << ", b=" << b
197 << std::endl;
198 }
199
200 // Find the step
201 h = (b - a) / N;
202
203 test(N, h, a, b, used_argv_parameters); // run self-test implementations
204
205 return 0;
206}
double k(double x)
Another test function.
double g(double x)
Another test function.
double f(double x)
A function f(x) that will be used to test the method.
double l(double x)
Another test function.
static void test()
Self-test implementations.
int main()
Main function.
int h(int key)
Contains the Simpson's method implementation.
constexpr uint32_t N
A struct to represent sparse table for min() as their invariant function, for the given array A....