C++ Mathematical Expression Toolkit (ExprTk) release
Loading...
Searching...
No Matches
exprtk_vectornorm.cpp
Go to the documentation of this file.
1/*
2 **************************************************************
3 * C++ Mathematical Expression Toolkit Library *
4 * *
5 * ExprTk L-Norm Of A Vector *
6 * Author: Arash Partow (1999-2024) *
7 * URL: https://www.partow.net/programming/exprtk/index.html *
8 * *
9 * Copyright notice: *
10 * Free use of the Mathematical Expression Toolkit Library is *
11 * permitted under the guidelines and in accordance with the *
12 * most current version of the MIT License. *
13 * https://www.opensource.org/licenses/MIT *
14 * SPDX-License-Identifier: MIT *
15 * *
16 **************************************************************
17*/
18
19
20#include <cmath>
21#include <cstdio>
22#include <string>
23#include <vector>
24
25#include "exprtk.hpp"
26
27
28template <typename T>
30{
36
37 using exprtk::igeneric_function<T>::operator();
38
40 : exprtk::igeneric_function<T>("V|VTT|VT|VTTT")
41 /*
42 Overloads:
43 0. V - vector
44 1. VTT - vector, r0, r1
45 2. VT - vector, l-power
46 3. VTTT - vector, l-power, r0, r1
47 */
48 {}
49
50 inline T operator()(const std::size_t& ps_index, parameter_list_t parameters)
51 {
52 unsigned int l = 2;
53
54 // Determine the l-power
55 if (
56 (2 == ps_index) ||
57 (3 == ps_index)
58 )
59 {
60 if (!scalar_t(parameters[1]).to_uint(l))
61 return std::numeric_limits<T>::quiet_NaN();
62 }
63
64 const vector_t vec(parameters[0]);
65
66 std::size_t r0 = 0;
67 std::size_t r1 = vec.size() - 1;
68
69 // Determine the range over the vector
70 if (
71 (1 == ps_index) ||
72 (3 == ps_index)
73 )
74 {
75 if (!scalar_t(parameters[(1 == ps_index) ? 1 : 2]).to_uint(r0))
76 return std::numeric_limits<T>::quiet_NaN();
77
78 if (!scalar_t(parameters[(1 == ps_index) ? 2 : 3]).to_uint(r1))
79 return std::numeric_limits<T>::quiet_NaN();
80 }
81
82 switch (l)
83 {
84 #define norm_def(N) case N : return norm_impl<N>(vec,r0,r1);
85 norm_def( 1) norm_def( 2) norm_def( 3) norm_def( 4)
86 norm_def( 5) norm_def( 6) norm_def( 7) norm_def( 8)
87 norm_def( 9) norm_def(10) norm_def(11) norm_def(12)
88 norm_def(13) norm_def(14) norm_def(15) norm_def(16)
89 norm_def(17) norm_def(18) norm_def(19) norm_def(20)
90 norm_def(21) norm_def(22) norm_def(23) norm_def(24)
91 norm_def(25) norm_def(26) norm_def(27) norm_def(28)
92 norm_def(29) norm_def(30) norm_def(31) norm_def(32)
93 default : return norm_impl(vec,l,r0,r1);
94 }
95 }
96
97 template <unsigned int Pow>
98 inline T norm_impl(const vector_t& vector, const std::size_t r0, const std::size_t r1)
99 {
100 T sum = T(0);
101
102 for (std::size_t i = r0; i <= r1; ++i)
103 {
104 sum += exprtk::details::numeric::fast_exp<T,Pow>::result(std::abs(vector[i]));
105 }
106
107 switch (Pow)
108 {
109 case 1 : return sum;
110 case 2 : return exprtk::details::numeric::sqrt(sum);
111 default : return exprtk::details::numeric::pow(sum, T(1) / Pow);
112 }
113 }
114
115 inline T norm_impl(const vector_t& vector, unsigned int pow, const std::size_t r0, const std::size_t r1)
116 {
117 T sum = T(0);
118
119 for (std::size_t i = r0; i <= r1; ++i)
120 {
121 sum += exprtk::details::numeric::pow(std::abs(vector[i]),T(pow));
122 }
123
124 return exprtk::details::numeric::pow(sum,T(1) / pow);
125 }
126};
127
128template <typename T>
130{
131 typedef exprtk::symbol_table<T> symbol_table_t;
132 typedef exprtk::expression<T> expression_t;
133 typedef exprtk::parser<T> parser_t;
134
135 T x[] = { T(1), T(2), T(3), T(4), T(5) };
136
137 std::vector<T> y;
138
139 y.push_back(T(5)); y.push_back(T(6));
140 y.push_back(T(7)); y.push_back(T(8));
141 y.push_back(T(9)); y.push_back(T(0));
142
143 symbol_table_t symbol_table;
144 symbol_table.add_vector("x", x);
145 symbol_table.add_vector("y", y);
146
147 norm<T> norm_;
148
149 symbol_table.add_function("norm",norm_);
150
151 const std::string vector_norm_program[] =
152 {
153 " norm(x) ",
154 " norm(x,1) ",
155 " norm(x,2) ",
156 " norm(x,3) ",
157 " norm(x,4) ",
158 " norm(x,5) ",
159 " norm(2x+1) ",
160 " norm(2x+1,1) ",
161 " norm(2x+1,2) ",
162 " norm(2x+1,3) ",
163 " norm(2x+1,4) ",
164 " norm(2x+1,5) ",
165 " norm(2x+y/3-4) ",
166 " norm(2x+y/3-4,1) ",
167 " norm(2x+y/3-4,2) ",
168 " norm(2x+y/3-4,3) ",
169 " norm(2x+y/3-4,4) ",
170 " norm(2x+y/3-4,5) "
171 };
172
173 const std::size_t vecnorm_program_size = sizeof(vector_norm_program) / sizeof(std::string);
174
175 parser_t parser;
176
177 for (std::size_t i = 0; i < vecnorm_program_size; ++i)
178 {
179 expression_t expression;
180 expression.register_symbol_table(symbol_table);
181
182 parser.compile(vector_norm_program[i], expression);
183
184 printf("%s = %15.8f\n",
185 vector_norm_program[i].c_str(),
186 expression.value());
187 }
188}
189
190int main()
191{
192 norm_of_vector<double>();
193 return 0;
194}
igeneric_function(const std::string &param_seq="", const return_type rtr_type=e_rtrn_scalar)
Definition exprtk.hpp:19667
#define norm_def(N)
void norm_of_vector()
int main()
T pow(const T v0, const T v1)
Definition exprtk.hpp:1527
std::size_t size() const
Definition exprtk.hpp:4772
exprtk::igeneric_function< T > igfun_t
T norm_impl(const vector_t &vector, const std::size_t r0, const std::size_t r1)
generic_type::scalar_view scalar_t
igfun_t::parameter_list_t parameter_list_t
T norm_impl(const vector_t &vector, unsigned int pow, const std::size_t r0, const std::size_t r1)
generic_type::vector_view vector_t
T operator()(const std::size_t &ps_index, parameter_list_t parameters)
igfun_t::generic_type generic_type