GNU Octave 10.1.0
A high-level interpreted language, primarily intended for numerical computations, mostly compatible with Matlab
 
Loading...
Searching...
No Matches
Quad.cc
Go to the documentation of this file.
1////////////////////////////////////////////////////////////////////////
2//
3// Copyright (C) 1993-2025 The Octave Project Developers
4//
5// See the file COPYRIGHT.md in the top-level directory of this
6// distribution or <https://octave.org/copyright/>.
7//
8// This file is part of Octave.
9//
10// Octave is free software: you can redistribute it and/or modify it
11// under the terms of the GNU General Public License as published by
12// the Free Software Foundation, either version 3 of the License, or
13// (at your option) any later version.
14//
15// Octave is distributed in the hope that it will be useful, but
16// WITHOUT ANY WARRANTY; without even the implied warranty of
17// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18// GNU General Public License for more details.
19//
20// You should have received a copy of the GNU General Public License
21// along with Octave; see the file COPYING. If not, see
22// <https://www.gnu.org/licenses/>.
23//
24////////////////////////////////////////////////////////////////////////
25
26#if defined (HAVE_CONFIG_H)
27# include "config.h"
28#endif
29
30#include "Array.h"
31#include "Quad.h"
32#include "f77-fcn.h"
33#include "lo-error.h"
34#include "quit.h"
35
36static integrand_fcn user_fcn;
37static float_integrand_fcn float_user_fcn;
38
39typedef F77_INT (*quad_fcn_ptr) (const double&, int&, double&);
40typedef F77_INT (*quad_float_fcn_ptr) (const float&, int&, float&);
41
42extern "C"
43{
45 F77_FUNC (dqagp, DQAGP) (quad_fcn_ptr, const F77_DBLE&, const F77_DBLE&,
46 const F77_INT&, const F77_DBLE *,
47 const F77_DBLE&, const F77_DBLE&, F77_DBLE&,
49 const F77_INT&, const F77_INT&,
50 F77_INT&, F77_INT *, F77_DBLE *);
51
54 const F77_INT&, const F77_DBLE&,
55 const F77_DBLE&, F77_DBLE&, F77_DBLE&,
57 const F77_INT&, const F77_INT&,
58 F77_INT&, F77_INT *, F77_DBLE *);
59
62 const F77_INT&, const F77_REAL *, const F77_REAL&,
63 const F77_REAL&, F77_REAL&, F77_REAL&, F77_INT&,
64 F77_INT&, const F77_INT&,
65 const F77_INT&, F77_INT&,
66 F77_INT *, F77_REAL *);
67
70 const F77_INT&, const F77_REAL&,
71 const F77_REAL&, F77_REAL&, F77_REAL&, F77_INT&,
72 F77_INT&, const F77_INT&,
73 const F77_INT&, F77_INT&,
74 F77_INT *, F77_REAL *);
75}
76
77static F77_INT
78user_function (const double& x, int&, double& result)
79{
80 result = (*user_fcn) (x);
81
82 return 0;
83}
84
85static F77_INT
86float_user_function (const float& x, int&, float& result)
87{
88 result = (*float_user_fcn) (x);
89
90 return 0;
91}
92
93double
95 double& abserr)
96{
97 F77_INT npts = octave::to_f77_int (m_singularities.numel () + 2);
98 double *points = m_singularities.rwdata ();
99 double result = 0.0;
100
101 F77_INT leniw = 183*npts - 122;
102 Array<F77_INT> iwork (dim_vector (leniw, 1));
103 F77_INT *piwork = iwork.rwdata ();
104
105 F77_INT lenw = 2*leniw - npts;
106 Array<double> work (dim_vector (lenw, 1));
107 double *pwork = work.rwdata ();
108
109 user_fcn = m_f;
110 F77_INT last;
111
112 double abs_tol = absolute_tolerance ();
113 double rel_tol = relative_tolerance ();
114
115 // NEVAL and IER are output only parameters and F77_INT can not be a
116 // wider type than octave_idx_type so we can create local variables
117 // here that are the correct type for the Fortran subroutine and then
118 // copy them to the function parameters without needing to preserve
119 // and pass the values to the Fortran subroutine.
120
121 F77_INT xneval, xier;
122
123 F77_XFCN (dqagp, DQAGP, (user_function, m_lower_limit, m_upper_limit,
124 npts, points, abs_tol, rel_tol, result,
125 abserr, xneval, xier, leniw, lenw, last,
126 piwork, pwork));
127
128 neval = xneval;
129 ier = xier;
130
131 return result;
132}
133
134float
136{
137 (*current_liboctave_error_handler) ("incorrect integration function called");
138}
139
140double
142 double& abserr)
143{
144 double result = 0.0;
145
146 F77_INT leniw = 128;
147 Array<F77_INT> iwork (dim_vector (leniw, 1));
148 F77_INT *piwork = iwork.rwdata ();
149
150 F77_INT lenw = 8*leniw;
151 Array<double> work (dim_vector (lenw, 1));
152 double *pwork = work.rwdata ();
153
154 user_fcn = m_f;
155 F77_INT last;
156
157 F77_INT inf;
158 switch (m_type)
159 {
160 case bound_to_inf:
161 inf = 1;
162 break;
163
164 case neg_inf_to_bound:
165 inf = -1;
166 break;
167
168 case doubly_infinite:
169 inf = 2;
170 break;
171
172 // We should have handled all possible enum values above. Rely on
173 // compiler diagnostics to warn if we haven't. For example, GCC's
174 // -Wswitch option, enabled by -Wall, will provide a warning.
175 }
176
177 double abs_tol = absolute_tolerance ();
178 double rel_tol = relative_tolerance ();
179
180 // NEVAL and IER are output only parameters and F77_INT can not be a
181 // wider type than octave_idx_type so we can create local variables
182 // here that are the correct type for the Fortran subroutine and then
183 // copy them to the function parameters without needing to preserve
184 // and pass the values to the Fortran subroutine.
185
186 F77_INT xneval, xier;
187
188 F77_XFCN (dqagi, DQAGI, (user_function, m_bound, inf, abs_tol, rel_tol,
189 result, abserr, xneval, xier, leniw, lenw,
190 last, piwork, pwork));
191
192 neval = xneval;
193 ier = xier;
194
195 return result;
196}
197
198float
200{
201 (*current_liboctave_error_handler) ("incorrect integration function called");
202}
203
204double
206{
207 (*current_liboctave_error_handler) ("incorrect integration function called");
208}
209
210float
212 float& abserr)
213{
214 F77_INT npts = octave::to_f77_int (m_singularities.numel () + 2);
215 float *points = m_singularities.rwdata ();
216 float result = 0.0;
217
218 F77_INT leniw = 183*npts - 122;
219 Array<F77_INT> iwork (dim_vector (leniw, 1));
220 F77_INT *piwork = iwork.rwdata ();
221
222 F77_INT lenw = 2*leniw - npts;
223 Array<float> work (dim_vector (lenw, 1));
224 float *pwork = work.rwdata ();
225
226 float_user_fcn = m_ff;
227 F77_INT last;
228
229 float abs_tol = single_precision_absolute_tolerance ();
230 float rel_tol = single_precision_relative_tolerance ();
231
232 // NEVAL and IER are output only parameters and F77_INT can not be a
233 // wider type than octave_idx_type so we can create local variables
234 // here that are the correct type for the Fortran subroutine and then
235 // copy them to the function parameters without needing to preserve
236 // and pass the values to the Fortran subroutine.
237
238 F77_INT xneval, xier;
239
240 F77_XFCN (qagp, QAGP, (float_user_function, m_lower_limit, m_upper_limit,
241 npts, points, abs_tol, rel_tol, result,
242 abserr, xneval, xier, leniw, lenw, last,
243 piwork, pwork));
244
245 neval = xneval;
246 ier = xier;
247
248 return result;
249}
250
251double
253{
254 (*current_liboctave_error_handler) ("incorrect integration function called");
255}
256
257float
259 float& abserr)
260{
261 float result = 0.0;
262
263 F77_INT leniw = 128;
264 Array<F77_INT> iwork (dim_vector (leniw, 1));
265 F77_INT *piwork = iwork.rwdata ();
266
267 F77_INT lenw = 8*leniw;
268 Array<float> work (dim_vector (lenw, 1));
269 float *pwork = work.rwdata ();
270
271 float_user_fcn = m_ff;
272 F77_INT last;
273
274 F77_INT inf;
275 switch (m_type)
276 {
277 case bound_to_inf:
278 inf = 1;
279 break;
280
281 case neg_inf_to_bound:
282 inf = -1;
283 break;
284
285 case doubly_infinite:
286 inf = 2;
287 break;
288
289 // We should have handled all possible enum values above. Rely on
290 // compiler diagnostics to warn if we haven't. For example, GCC's
291 // -Wswitch option, enabled by -Wall, will provide a warning.
292 }
293
294 float abs_tol = single_precision_absolute_tolerance ();
295 float rel_tol = single_precision_relative_tolerance ();
296
297 // NEVAL and IER are output only parameters and F77_INT can not be a
298 // wider type than octave_idx_type so we can create local variables
299 // here that are the correct type for the Fortran subroutine and then
300 // copy them to the function parameters without needing to preserve
301 // and pass the values to the Fortran subroutine.
302
303 F77_INT xneval, xier;
304
305 F77_XFCN (qagi, QAGI, (float_user_function, m_bound, inf, abs_tol, rel_tol,
306 result, abserr, xneval, xier, leniw, lenw,
307 last, piwork, pwork));
308
309 neval = xneval;
310 ier = xier;
311
312 return result;
313}
F77_INT(* quad_float_fcn_ptr)(const float &, int &, float &)
Definition Quad.cc:40
F77_RET_T F77_FUNC(dqagp, DQAGP)(quad_fcn_ptr
F77_INT(* quad_fcn_ptr)(const double &, int &, double &)
Definition Quad.cc:39
double(* integrand_fcn)(double x)
Definition Quad.h:34
float(* float_integrand_fcn)(float x)
Definition Quad.h:35
N Dimensional Array with copy-on-write semantics.
Definition Array.h:130
T * rwdata()
Size of the specified dimension.
octave_idx_type numel() const
Number of elements in the array.
Definition Array.h:418
double do_integrate(octave_idx_type &ier, octave_idx_type &neval, double &abserr)
Definition Quad.cc:94
OCTAVE_NORETURN double do_integrate(octave_idx_type &ier, octave_idx_type &neval, double &abserr)
Definition Quad.cc:205
@ doubly_infinite
Definition Quad.h:229
@ neg_inf_to_bound
Definition Quad.h:229
OCTAVE_NORETURN double do_integrate(octave_idx_type &ier, octave_idx_type &neval, double &abserr)
Definition Quad.cc:252
double do_integrate(octave_idx_type &ier, octave_idx_type &neval, double &abserr)
Definition Quad.cc:141
@ bound_to_inf
Definition Quad.h:162
@ doubly_infinite
Definition Quad.h:162
@ neg_inf_to_bound
Definition Quad.h:162
float_integrand_fcn m_ff
Definition Quad.h:116
integrand_fcn m_f
Definition Quad.h:115
Vector representing the dimensions (size) of an Array.
Definition dim-vector.h:90
subroutine dqagi(f, bound, inf, epsabs, epsrel, result, abserr, neval, ier, limit, lenw, last, iwork, work)
Definition dqagi.f:3
subroutine dqagp(f, a, b, npts2, points, epsabs, epsrel, result, abserr, neval, ier, leniw, lenw, last, iwork, work)
Definition dqagp.f:3
float F77_REAL
Definition f77-fcn.h:303
#define F77_XFCN(f, F, args)
Definition f77-fcn.h:45
double F77_DBLE
Definition f77-fcn.h:302
octave_f77_int_type F77_INT
Definition f77-fcn.h:306
F77_RET_T(F77_CONST_CHAR_ARG_DECL, F77_CONST_CHAR_ARG_DECL, F77_CONST_CHAR_ARG_DECL, const F77_INT &, const F77_INT &, const F77_INT &, F77_INT &, F77_INT &, F77_DBLE *, const F77_INT &, F77_DBLE *, const F77_INT &, F77_DBLE *, F77_DBLE *, F77_DBLE *, const F77_INT &, F77_DBLE *, const F77_INT &, F77_DBLE *, const F77_INT &, F77_DBLE *, F77_INT *, F77_INT &F77_CHAR_ARG_LEN_DECL F77_CHAR_ARG_LEN_DECL F77_CHAR_ARG_LEN_DECL)
F77_RET_T const F77_DBLE * x
subroutine qagi(f, bound, inf, epsabs, epsrel, result, abserr, neval, ier, limit, lenw, last, iwork, work)
Definition qagi.f:3
subroutine qagp(f, a, b, npts2, points, epsabs, epsrel, result, abserr, neval, ier, leniw, lenw, last, iwork, work)
Definition qagp.f:3