source: XIOS/dev/dev_olga/src/extern/blitz/include/blitz/funcs.h @ 1022

Last change on this file since 1022 was 1022, checked in by mhnguyen, 7 years ago
File size: 30.9 KB
Line 
1// -*- C++ -*-
2/***************************************************************************
3 * blitz/funcs.h            Function objects for math functions
4 *
5 * $Id$
6 *
7 * Copyright (C) 1997-2011 Todd Veldhuizen <tveldhui@acm.org>
8 *
9 * This file is a part of Blitz.
10 *
11 * Blitz is free software: you can redistribute it and/or modify
12 * it under the terms of the GNU Lesser General Public License
13 * as published by the Free Software Foundation, either version 3
14 * of the License, or (at your option) any later version.
15 *
16 * Blitz is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19 * GNU Lesser General Public License for more details.
20 *
21 * You should have received a copy of the GNU Lesser General Public
22 * License along with Blitz.  If not, see <http://www.gnu.org/licenses/>.
23 *
24 * Suggestions:          blitz-devel@lists.sourceforge.net
25 * Bugs:                 blitz-support@lists.sourceforge.net   
26 *
27 * For more information, please see the Blitz++ Home Page:
28 *    https://sourceforge.net/projects/blitz/
29 *
30 *************************************************************************/
31
32#ifndef BZ_FUNCS_H
33#define BZ_FUNCS_H
34
35#include <blitz/blitz.h>
36#include <blitz/promote.h>
37#include <blitz/prettyprint.h>
38
39#include <cstdlib>
40
41BZ_NAMESPACE(blitz)
42   
43/* Helper functions. We use SFINAE to make these apply only for
44   non-blitz numerical types (POD and complex), because otherwise they
45   match against Array, etc, better than the ET versions that take
46   ETBase parameters. */
47   
48template<typename T, bool b> struct _bz_isnot_blitz {};
49template<typename T> struct _bz_isnot_blitz<T, true> {typedef T Type;};
50template<typename T, bool b> struct _bz_isnot_blitz<std::complex<T>, b> {typedef std::complex<T> Type;};
51
52template <typename T>
53inline typename _bz_isnot_blitz<T, std::numeric_limits<T>::is_specialized>::Type
54pow2(const T x)
55{ return x*x; }
56
57template <typename T>
58inline typename _bz_isnot_blitz<T, std::numeric_limits<T>::is_specialized>::Type
59pow3(const T x)
60{ return x*x*x; }
61
62template <typename T>
63inline typename _bz_isnot_blitz<T, std::numeric_limits<T>::is_specialized>::Type
64pow4(const T x)
65{ return x*x*x*x; }
66
67template <typename T>
68inline typename _bz_isnot_blitz<T, std::numeric_limits<T>::is_specialized>::Type
69pow5(const T x)
70{ return x*x*x*x*x; }
71
72template <typename T>
73inline typename _bz_isnot_blitz<T, std::numeric_limits<T>::is_specialized>::Type
74pow6(const T x)
75{ return x*x*x*x*x*x; }
76
77template <typename T>
78inline typename _bz_isnot_blitz<T, std::numeric_limits<T>::is_specialized>::Type
79pow7(const T x)
80{ return x*x*x*x*x*x*x; }
81
82template <typename T>
83inline typename _bz_isnot_blitz<T, std::numeric_limits<T>::is_specialized>::Type
84pow8(const T x)
85{ return x*x*x*x*x*x*x*x; }
86
87/** This class can be used to select between two types based on a bool. */
88template<bool b, typename T1, typename T2> struct ifthenelse {
89  typedef T1 Type;
90};
91template<typename T1, typename T2> struct ifthenelse<false,T1,T2> {
92  typedef T2 Type;
93};
94
95
96/* Unary functions whose return type is the same as the argument (if
97   coerce_int is false) or (if coerce_int is true) returns a double
98   for int arguments. (This is how gcc defines its math functions, so
99   we should do the same.) Coerce_int is true except for the functions
100   that can also meaningfully operate on ints.  */
101   
102#define BZ_DEFINE_UNARY_FUNC(name,fun,coerce_int)                    \
103template<typename T_numtype1>                                        \
104struct name {                                                        \
105  typedef typename ifthenelse<coerce_int,typename ifthenelse<numeric_limits<T_numtype1>::is_integer,double,T_numtype1>::Type,T_numtype1>::Type T_numtype; \
106                                                                     \
107    static inline T_numtype                                          \
108    apply(const T_numtype1 a)                                        \
109    { return fun(a); }                                               \
110                                                                     \
111    template<typename T1>                                            \
112    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,        \
113        BZ_BLITZ_SCOPE(prettyPrintFormat) &format, const T1& t1)     \
114    {                                                                \
115        str += #fun;                                                 \
116        str += "(";                                                  \
117        t1.prettyPrint(str, format);                                 \
118        str += ")";                                                  \
119    }                                                                \
120};
121
122BZ_DEFINE_UNARY_FUNC(Fn_abs,BZ_MATHFN_SCOPE(abs),false)
123BZ_DEFINE_UNARY_FUNC(Fn_acos,BZ_MATHFN_SCOPE(acos),true)
124BZ_DEFINE_UNARY_FUNC(Fn_asin,BZ_MATHFN_SCOPE(asin),true)
125BZ_DEFINE_UNARY_FUNC(Fn_atan,BZ_MATHFN_SCOPE(atan),true)
126BZ_DEFINE_UNARY_FUNC(Fn_ceil,BZ_MATHFN_SCOPE(ceil),true)
127BZ_DEFINE_UNARY_FUNC(Fn_cos,BZ_MATHFN_SCOPE(cos),true)
128BZ_DEFINE_UNARY_FUNC(Fn_cosh,BZ_MATHFN_SCOPE(cosh),true)
129BZ_DEFINE_UNARY_FUNC(Fn_exp,BZ_MATHFN_SCOPE(exp),true)
130BZ_DEFINE_UNARY_FUNC(Fn_fabs,BZ_MATHFN_SCOPE(fabs),true)
131BZ_DEFINE_UNARY_FUNC(Fn_floor,BZ_MATHFN_SCOPE(floor),true)
132BZ_DEFINE_UNARY_FUNC(Fn_log,BZ_MATHFN_SCOPE(log),true)
133BZ_DEFINE_UNARY_FUNC(Fn_log10,BZ_MATHFN_SCOPE(log10),true)
134BZ_DEFINE_UNARY_FUNC(Fn_sin,BZ_MATHFN_SCOPE(sin),true)
135BZ_DEFINE_UNARY_FUNC(Fn_sinh,BZ_MATHFN_SCOPE(sinh),true)
136BZ_DEFINE_UNARY_FUNC(Fn_sqrt,BZ_MATHFN_SCOPE(sqrt),true)
137BZ_DEFINE_UNARY_FUNC(Fn_tan,BZ_MATHFN_SCOPE(tan),true)
138BZ_DEFINE_UNARY_FUNC(Fn_tanh,BZ_MATHFN_SCOPE(tanh),true)
139
140#ifdef BZ_HAVE_IEEE_MATH
141BZ_DEFINE_UNARY_FUNC(Fn_acosh,BZ_IEEEMATHFN_SCOPE(acosh),true)
142BZ_DEFINE_UNARY_FUNC(Fn_asinh,BZ_IEEEMATHFN_SCOPE(asinh),true)
143BZ_DEFINE_UNARY_FUNC(Fn_atanh,BZ_IEEEMATHFN_SCOPE(atanh),true)
144BZ_DEFINE_UNARY_FUNC(Fn_cbrt,BZ_IEEEMATHFN_SCOPE(cbrt),true)
145BZ_DEFINE_UNARY_FUNC(Fn_erf,BZ_IEEEMATHFN_SCOPE(erf),true)
146BZ_DEFINE_UNARY_FUNC(Fn_erfc,BZ_IEEEMATHFN_SCOPE(erfc),true)
147BZ_DEFINE_UNARY_FUNC(Fn_expm1,BZ_IEEEMATHFN_SCOPE(expm1),true)
148BZ_DEFINE_UNARY_FUNC(Fn_j0,BZ_IEEEMATHFN_SCOPE(j0),true)
149BZ_DEFINE_UNARY_FUNC(Fn_j1,BZ_IEEEMATHFN_SCOPE(j1),true)
150BZ_DEFINE_UNARY_FUNC(Fn_lgamma,BZ_IEEEMATHFN_SCOPE(lgamma),true)
151BZ_DEFINE_UNARY_FUNC(Fn_logb,BZ_IEEEMATHFN_SCOPE(logb),true)
152BZ_DEFINE_UNARY_FUNC(Fn_log1p,BZ_IEEEMATHFN_SCOPE(log1p),true)
153BZ_DEFINE_UNARY_FUNC(Fn_rint,BZ_IEEEMATHFN_SCOPE(rint),true)
154BZ_DEFINE_UNARY_FUNC(Fn_y0,BZ_IEEEMATHFN_SCOPE(y0),true)
155BZ_DEFINE_UNARY_FUNC(Fn_y1,BZ_IEEEMATHFN_SCOPE(y1),true)
156#endif
157   
158#ifdef BZ_HAVE_SYSTEM_V_MATH
159BZ_DEFINE_UNARY_FUNC(Fn__class,BZ_IEEEMATHFN_SCOPE(_class),true)
160BZ_DEFINE_UNARY_FUNC(Fn_nearest,BZ_IEEEMATHFN_SCOPE(nearest),true)
161BZ_DEFINE_UNARY_FUNC(Fn_rsqrt,BZ_IEEEMATHFN_SCOPE(rsqrt),true)
162#endif
163   
164BZ_DEFINE_UNARY_FUNC(Fn_sqr,BZ_BLITZ_SCOPE(pow2),false)
165BZ_DEFINE_UNARY_FUNC(Fn_cube,BZ_BLITZ_SCOPE(pow3),false)
166BZ_DEFINE_UNARY_FUNC(Fn_pow4,BZ_BLITZ_SCOPE(pow4),false)
167BZ_DEFINE_UNARY_FUNC(Fn_pow5,BZ_BLITZ_SCOPE(pow5),false)
168BZ_DEFINE_UNARY_FUNC(Fn_pow6,BZ_BLITZ_SCOPE(pow6),false)
169BZ_DEFINE_UNARY_FUNC(Fn_pow7,BZ_BLITZ_SCOPE(pow7),false)
170BZ_DEFINE_UNARY_FUNC(Fn_pow8,BZ_BLITZ_SCOPE(pow8),false)
171
172/* Unary functions that return a specified type */
173   
174#define BZ_DEFINE_UNARY_FUNC_RET(name,fun,ret)                       \
175template<typename T_numtype1>                                        \
176struct name {                                                        \
177    typedef ret T_numtype;                                           \
178                                                                     \
179    static inline T_numtype                                          \
180    apply(const T_numtype1 a)                                        \
181    { return fun(a); }                                               \
182                                                                     \
183    template<typename T1>                                            \
184    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,        \
185        BZ_BLITZ_SCOPE(prettyPrintFormat) &format, const T1& t1)     \
186    {                                                                \
187        str += #fun;                                                 \
188        str += "(";                                                  \
189        t1.prettyPrint(str, format);                                 \
190        str += ")";                                                  \
191    }                                                                \
192};
193
194#ifdef BZ_HAVE_IEEE_MATH
195BZ_DEFINE_UNARY_FUNC_RET(Fn_ilogb,BZ_IEEEMATHFN_SCOPE(ilogb),int)
196#endif
197   
198#ifdef BZ_HAVE_SYSTEM_V_MATH
199BZ_DEFINE_UNARY_FUNC_RET(Fn_itrunc,BZ_IEEEMATHFN_SCOPE(itrunc),int)
200BZ_DEFINE_UNARY_FUNC_RET(Fn_uitrunc,BZ_IEEEMATHFN_SCOPE(uitrunc),unsigned int)
201#endif
202   
203   
204#ifdef BZ_HAVE_COMPLEX
205/* Specialization of unary functor for complex type */
206   
207#define BZ_DEFINE_UNARY_CFUNC(name,fun)                              \
208template<typename T>                                                 \
209struct name< BZ_STD_SCOPE(complex)<T> > {                            \
210    typedef BZ_STD_SCOPE(complex)<T> T_numtype1;                     \
211    typedef BZ_STD_SCOPE(complex)<T> T_numtype;                      \
212                                                                     \
213    static inline T_numtype                                          \
214    apply(const T_numtype1 a)                                        \
215    { return fun(a); }                                               \
216                                                                     \
217    template<typename T1>                                            \
218    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,        \
219        BZ_BLITZ_SCOPE(prettyPrintFormat) &format, const T1& t1)     \
220    {                                                                \
221        str += #fun;                                                 \
222        str += "(";                                                  \
223        t1.prettyPrint(str, format);                                 \
224        str += ")";                                                  \
225    }                                                                \
226};
227
228#ifdef BZ_HAVE_COMPLEX_FCNS
229BZ_DEFINE_UNARY_FUNC(Fn_conj,BZ_CMATHFN_SCOPE(conj),false)
230#endif
231
232#ifdef BZ_HAVE_COMPLEX_MATH1
233BZ_DEFINE_UNARY_CFUNC(Fn_cos,BZ_CMATHFN_SCOPE(cos))
234BZ_DEFINE_UNARY_CFUNC(Fn_cosh,BZ_CMATHFN_SCOPE(cosh))
235BZ_DEFINE_UNARY_CFUNC(Fn_exp,BZ_CMATHFN_SCOPE(exp))
236BZ_DEFINE_UNARY_CFUNC(Fn_log,BZ_CMATHFN_SCOPE(log))
237BZ_DEFINE_UNARY_CFUNC(Fn_log10,BZ_CMATHFN_SCOPE(log10))
238BZ_DEFINE_UNARY_CFUNC(Fn_sin,BZ_CMATHFN_SCOPE(sin))
239BZ_DEFINE_UNARY_CFUNC(Fn_sinh,BZ_CMATHFN_SCOPE(sinh))
240BZ_DEFINE_UNARY_CFUNC(Fn_sqrt,BZ_CMATHFN_SCOPE(sqrt))
241BZ_DEFINE_UNARY_CFUNC(Fn_tan,BZ_CMATHFN_SCOPE(tan))
242BZ_DEFINE_UNARY_CFUNC(Fn_tanh,BZ_CMATHFN_SCOPE(tanh))
243#endif // BZ_HAVE_COMPLEX_MATH1
244
245BZ_DEFINE_UNARY_CFUNC(Fn_sqr,BZ_BLITZ_SCOPE(pow2))
246BZ_DEFINE_UNARY_CFUNC(Fn_cube,BZ_BLITZ_SCOPE(pow3))
247BZ_DEFINE_UNARY_CFUNC(Fn_pow4,BZ_BLITZ_SCOPE(pow4))
248BZ_DEFINE_UNARY_CFUNC(Fn_pow5,BZ_BLITZ_SCOPE(pow5))
249BZ_DEFINE_UNARY_CFUNC(Fn_pow6,BZ_BLITZ_SCOPE(pow6))
250BZ_DEFINE_UNARY_CFUNC(Fn_pow7,BZ_BLITZ_SCOPE(pow7))
251BZ_DEFINE_UNARY_CFUNC(Fn_pow8,BZ_BLITZ_SCOPE(pow8))
252
253/* Unary functions that apply only to complex<T> and return T */
254   
255#define BZ_DEFINE_UNARY_CFUNC2(name,fun)                             \
256template<typename T_numtype1>                                        \
257struct name;                                                         \
258                                                                     \
259template<typename T>                                                 \
260struct name< BZ_STD_SCOPE(complex)<T> > {                            \
261    typedef BZ_STD_SCOPE(complex)<T> T_numtype1;                     \
262    typedef T T_numtype;                                             \
263                                                                     \
264    static inline T_numtype                                          \
265    apply(const T_numtype1 a)                                        \
266    { return fun(a); }                                               \
267                                                                     \
268    template<typename T1>                                            \
269    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,        \
270        BZ_BLITZ_SCOPE(prettyPrintFormat) &format, const T1& t1)     \
271    {                                                                \
272        str += #fun;                                                 \
273        str += "(";                                                  \
274        t1.prettyPrint(str, format);                                 \
275        str += ")";                                                  \
276    }                                                                \
277};
278
279#ifdef BZ_HAVE_COMPLEX_FCNS
280BZ_DEFINE_UNARY_CFUNC2(Fn_abs,BZ_CMATHFN_SCOPE(abs))
281BZ_DEFINE_UNARY_CFUNC2(Fn_arg,BZ_CMATHFN_SCOPE(arg))
282BZ_DEFINE_UNARY_CFUNC2(Fn_imag,BZ_CMATHFN_SCOPE(imag))
283BZ_DEFINE_UNARY_CFUNC2(Fn_norm,BZ_CMATHFN_SCOPE(norm))
284BZ_DEFINE_UNARY_CFUNC2(Fn_real,BZ_CMATHFN_SCOPE(real))
285#endif // BZ_HAVE_COMPLEX_FCNS
286   
287#endif // BZ_HAVE_COMPLEX
288   
289/* Binary functions that return type based on type promotion */
290   
291#define BZ_DEFINE_BINARY_FUNC(name,fun)                              \
292template<typename T_numtype1, typename T_numtype2>                   \
293struct name {                                                        \
294    typedef BZ_PROMOTE(T_numtype1, T_numtype2) T_numtype;            \
295                                                                     \
296    static inline T_numtype                                          \
297    apply(T_numtype1 a, T_numtype2 b)                                \
298    { return fun(a,b); }                                             \
299                                                                     \
300    template<typename T1, typename T2>                               \
301    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,        \
302        BZ_BLITZ_SCOPE(prettyPrintFormat) &format, const T1& t1,     \
303        const T2& t2)                                                \
304    {                                                                \
305        str += #fun;                                                 \
306        str += "(";                                                  \
307        t1.prettyPrint(str, format);                                 \
308        str += ",";                                                  \
309        t2.prettyPrint(str, format);                                 \
310        str += ")";                                                  \
311    }                                                                \
312};
313
314BZ_DEFINE_BINARY_FUNC(Fn_atan2,BZ_MATHFN_SCOPE(atan2))
315BZ_DEFINE_BINARY_FUNC(Fn_fmod,BZ_MATHFN_SCOPE(fmod))
316BZ_DEFINE_BINARY_FUNC(Fn_pow,BZ_MATHFN_SCOPE(pow))
317   
318#ifdef BZ_HAVE_SYSTEM_V_MATH
319BZ_DEFINE_BINARY_FUNC(Fn_copysign,BZ_IEEEMATHFN_SCOPE(copysign))
320BZ_DEFINE_BINARY_FUNC(Fn_drem,BZ_IEEEMATHFN_SCOPE(drem))
321BZ_DEFINE_BINARY_FUNC(Fn_hypot,BZ_IEEEMATHFN_SCOPE(hypot))
322BZ_DEFINE_BINARY_FUNC(Fn_nextafter,BZ_IEEEMATHFN_SCOPE(nextafter))
323BZ_DEFINE_BINARY_FUNC(Fn_remainder,BZ_IEEEMATHFN_SCOPE(remainder))
324BZ_DEFINE_BINARY_FUNC(Fn_scalb,BZ_IEEEMATHFN_SCOPE(scalb))
325#endif
326   
327/* Binary functions that return a specified type */
328   
329#define BZ_DEFINE_BINARY_FUNC_RET(name,fun,ret)                      \
330template<typename T_numtype1, typename T_numtype2>                   \
331struct name {                                                        \
332    typedef ret T_numtype;                                           \
333                                                                     \
334    static inline T_numtype                                          \
335    apply(T_numtype1 a, T_numtype2 b)                                \
336    { return fun(a,b); }                                             \
337                                                                     \
338    template<typename T1, typename T2>                               \
339    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,        \
340        BZ_BLITZ_SCOPE(prettyPrintFormat) &format, const T1& t1,     \
341        const T2& t2)                                                \
342    {                                                                \
343        str += #fun;                                                 \
344        str += "(";                                                  \
345        t1.prettyPrint(str, format);                                 \
346        str += ",";                                                  \
347        t2.prettyPrint(str, format);                                 \
348        str += ")";                                                  \
349    }                                                                \
350};
351
352#ifdef BZ_HAVE_SYSTEM_V_MATH
353BZ_DEFINE_BINARY_FUNC_RET(Fn_unordered,BZ_IEEEMATHFN_SCOPE(unordered),int)
354#endif
355   
356#ifdef BZ_HAVE_COMPLEX
357/* Specialization of binary functor for complex type */
358   
359#define BZ_DEFINE_BINARY_CFUNC(name,fun)                             \
360template<typename T>                                                 \
361struct name< BZ_STD_SCOPE(complex)<T>, BZ_STD_SCOPE(complex)<T> > {  \
362    typedef BZ_STD_SCOPE(complex)<T> T_numtype1;                     \
363    typedef BZ_STD_SCOPE(complex)<T> T_numtype2;                     \
364    typedef BZ_STD_SCOPE(complex)<T> T_numtype;                      \
365                                                                     \
366    static inline T_numtype                                          \
367    apply(T_numtype1 a, T_numtype2 b)                                \
368    { return fun(a,b); }                                             \
369                                                                     \
370    template<typename T1, typename T2>                               \
371    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,        \
372        BZ_BLITZ_SCOPE(prettyPrintFormat) &format, const T1& t1,     \
373        const T2& t2)                                                \
374    {                                                                \
375        str += #fun;                                                 \
376        str += "(";                                                  \
377        t1.prettyPrint(str, format);                                 \
378        str += ",";                                                  \
379        t2.prettyPrint(str, format);                                 \
380        str += ")";                                                  \
381    }                                                                \
382};                                                                   \
383                                                                     \
384template<typename T>                                                 \
385struct name< BZ_STD_SCOPE(complex)<T>, T > {                         \
386    typedef BZ_STD_SCOPE(complex)<T> T_numtype1;                     \
387    typedef T T_numtype2;                                            \
388    typedef BZ_STD_SCOPE(complex)<T> T_numtype;                      \
389                                                                     \
390    static inline T_numtype                                          \
391    apply(T_numtype1 a, T_numtype2 b)                                \
392    { return fun(a,b); }                                             \
393                                                                     \
394    template<typename T1, typename T2>                               \
395    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,        \
396        BZ_BLITZ_SCOPE(prettyPrintFormat) &format, const T1& t1,     \
397        const T2& t2)                                                \
398    {                                                                \
399        str += #fun;                                                 \
400        str += "(";                                                  \
401        t1.prettyPrint(str, format);                                 \
402        str += ",";                                                  \
403        t2.prettyPrint(str, format);                                 \
404        str += ")";                                                  \
405    }                                                                \
406};                                                                   \
407                                                                     \
408template<typename T>                                                 \
409struct name< T, BZ_STD_SCOPE(complex)<T> > {                         \
410    typedef T T_numtype1;                                            \
411    typedef BZ_STD_SCOPE(complex)<T> T_numtype2;                     \
412    typedef BZ_STD_SCOPE(complex)<T> T_numtype;                      \
413                                                                     \
414    static inline T_numtype                                          \
415    apply(T_numtype1 a, T_numtype2 b)                                \
416    { return fun(a,b); }                                             \
417                                                                     \
418    template<typename T1, typename T2>                               \
419    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,        \
420        BZ_BLITZ_SCOPE(prettyPrintFormat) &format, const T1& t1,     \
421        const T2& t2)                                                \
422    {                                                                \
423        str += #fun;                                                 \
424        str += "(";                                                  \
425        t1.prettyPrint(str, format);                                 \
426        str += ",";                                                  \
427        t2.prettyPrint(str, format);                                 \
428        str += ")";                                                  \
429    }                                                                \
430};
431
432#ifdef BZ_HAVE_COMPLEX_MATH1
433BZ_DEFINE_BINARY_CFUNC(Fn_pow,BZ_CMATHFN_SCOPE(pow))
434#endif
435
436/* Binary functions that apply only to T and return complex<T> */
437   
438#define BZ_DEFINE_BINARY_FUNC_CRET(name,fun)                         \
439template<typename T_numtype1, typename T_numtype2>                   \
440struct name;                                                         \
441                                                                     \
442template<typename T>                                                 \
443struct name<T, T> {                                                  \
444    typedef T T_numtype1;                                            \
445    typedef T T_numtype2;                                            \
446    typedef BZ_STD_SCOPE(complex)<T> T_numtype;                      \
447                                                                     \
448    static inline T_numtype                                          \
449    apply(T_numtype1 a, T_numtype2 b)                                \
450    { return fun(a,b); }                                             \
451                                                                     \
452    template<typename T1, typename T2>                               \
453    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,        \
454        BZ_BLITZ_SCOPE(prettyPrintFormat) &format, const T1& t1,     \
455        const T2& t2)                                                \
456    {                                                                \
457        str += #fun;                                                 \
458        str += "(";                                                  \
459        t1.prettyPrint(str, format);                                 \
460        str += ",";                                                  \
461        t2.prettyPrint(str, format);                                 \
462        str += ")";                                                  \
463    }                                                                \
464};
465
466#ifdef BZ_HAVE_COMPLEX_FCNS
467BZ_DEFINE_BINARY_FUNC_CRET(Fn_polar,BZ_CMATHFN_SCOPE(polar))
468#endif
469   
470#endif // BZ_HAVE_COMPLEX
471   
472/* Ternary functions that return type based on type promotion */
473   
474#define BZ_DEFINE_TERNARY_FUNC(name,fun)                             \
475template <typename P_numtype1, typename P_numtype2,                  \
476          typename P_numtype3>                                       \
477struct name {                                                        \
478    typedef BZ_PROMOTE(P_numtype1,                                   \
479            BZ_PROMOTE(P_numtype2,P_numtype3)) T_numtype;            \
480                                                                     \
481    static inline T_numtype                                          \
482    apply(P_numtype1 x, P_numtype2 y, P_numtype3 z)                  \
483    { return fun(x,y,z); }                                           \
484                                                                     \
485    template <typename T1, typename T2, typename T3>                 \
486    static void prettyPrint(BZ_STD_SCOPE(string) &str,               \
487        BZ_BLITZ_SCOPE(prettyPrintFormat) &format,                   \
488        const T1& a,const T2& b, const T3& c)                        \
489    {                                                                \
490        str += #fun;                                                 \
491        str += "(";                                                  \
492        a.prettyPrint(str,format);                                   \
493        str += ",";                                                  \
494        b.prettyPrint(str,format);                                   \
495        str += ",";                                                  \
496        c.prettyPrint(str,format);                                   \
497        str += ")";                                                  \
498    }                                                                \
499};
500
501/* Ternary functions that return a specified type */
502   
503#define BZ_DEFINE_TERNARY_FUNC_RET(name,fun,ret)                     \
504template <typename P_numtype1, typename P_numtype2,                  \
505          typename P_numtype3>                                       \
506struct name {                                                        \
507    typedef ret T_numtype;                                           \
508                                                                     \
509    static inline T_numtype                                          \
510    apply(P_numtype1 x, P_numtype2 y, P_numtype3 z)                  \
511    { return fun(x,y,z); }                                           \
512                                                                     \
513    template <typename T1, typename T2, typename T3>                 \
514    static void prettyPrint(BZ_STD_SCOPE(string) &str,               \
515        BZ_BLITZ_SCOPE(prettyPrintFormat) &format,                   \
516        const T1& a,const T2& b, const T3& c)                        \
517    {                                                                \
518        str += #fun;                                                 \
519        str += "(";                                                  \
520        a.prettyPrint(str,format);                                   \
521        str += ",";                                                  \
522        b.prettyPrint(str,format);                                   \
523        str += ",";                                                  \
524        c.prettyPrint(str,format);                                   \
525        str += ")";                                                  \
526    }                                                                \
527};
528
529/* Quaternary functions that return type based on type promotion */
530
531#define BZ_DEFINE_QUATERNARY_FUNC(name,fun)                             \
532  template<typename T_numtype1, typename T_numtype2,                    \
533           typename T_numtype3, typename T_numtype4>                    \
534  struct name {                                                         \
535    typedef BZ_PROMOTE(BZ_PROMOTE(T_numtype1, T_numtype2),              \
536                       BZ_PROMOTE(T_numtype3, T_numtype4)) T_numtype;   \
537                                                                        \
538    static inline T_numtype                                             \
539    apply(const T_numtype1 a, const T_numtype2 b,                       \
540          const T_numtype3 c, const T_numtype4 d)                       \
541  { return fun(a,b,c,d); }                                              \
542                                                                        \
543    template<typename T1, typename T2,                                  \
544             typename T3, typename T4>                                  \
545    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,           \
546                                   BZ_BLITZ_SCOPE(prettyPrintFormat) &format, \
547                                   const T1& t1,const T2& t2, const T3& t3, const T4& t4) \
548    {                                                                   \
549      str += #fun;                                                      \
550      str += "(";                                                       \
551      t1.prettyPrint(str, format);                                      \
552      str += ",";                                                       \
553      t2.prettyPrint(str, format);                                      \
554      str += ",";                                                       \
555      t3.prettyPrint(str, format);                                      \
556      str += ",";                                                       \
557      t4.prettyPrint(str, format);                                      \
558      str += ")";                                                       \
559    }                                                                   \
560  };
561
562   
563/* These functions don't quite fit the usual patterns */
564   
565#ifdef BZ_HAVE_IEEE_MATH
566// isnan()    Nonzero if NaNS or NaNQ
567template<typename T_numtype1>
568struct Fn_isnan {
569    typedef int T_numtype;
570   
571    static inline T_numtype
572    apply(T_numtype1 a)
573    {
574#ifdef BZ_ISNAN_IN_NAMESPACE_STD
575        return BZ_STD_SCOPE(isnan)(a);
576#else
577        return BZ_IEEEMATHFN_SCOPE(isnan)(a);
578#endif
579    }
580   
581    template<typename T1>
582    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,
583        prettyPrintFormat& format, const T1& t1)
584    {
585        str += "isnan";
586        str += "(";
587        t1.prettyPrint(str, format);
588        str += ")";
589    }
590};
591#endif // BZ_HAVE_IEEE_MATH
592
593
594// Blitz cast() function
595template<typename T_numtype1, typename T_cast>
596struct Cast {
597    typedef T_cast T_numtype;
598   
599    static inline T_numtype
600    apply(T_numtype1 a)
601    { return T_numtype(a); }
602
603    template<typename T1>
604    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,
605        prettyPrintFormat& format, const T1& t1)
606    {
607        str += BZ_DEBUG_TEMPLATE_AS_STRING_LITERAL(T_cast);
608        str += "(";
609        t1.prettyPrint(str, format);
610        str += ")";
611    }
612};
613
614// Blitz min/max functions
615template<typename T_numtype1, typename T_numtype2>
616struct Min {
617    typedef BZ_PROMOTE(T_numtype1, T_numtype2) T_numtype;
618
619    static inline T_numtype
620    apply(T_numtype1 a, T_numtype2 b)
621    { return (a < b ? a : b); }
622
623    template<typename T1, typename T2>
624    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,
625        prettyPrintFormat& format, const T1& t1, const T2& t2)
626    {
627        str += "min(";
628        t1.prettyPrint(str, format);
629        str += ",";
630        t2.prettyPrint(str, format);
631        str += ")";
632    }
633};
634
635template<typename T_numtype1, typename T_numtype2>
636struct Max {
637    typedef BZ_PROMOTE(T_numtype1, T_numtype2) T_numtype;
638
639    static inline T_numtype
640    apply(T_numtype1 a, T_numtype2 b)
641    { return (a > b ? a : b); }
642
643    template<typename T1, typename T2>
644    static inline void prettyPrint(BZ_STD_SCOPE(string) &str,
645        prettyPrintFormat& format, const T1& t1, const T2& t2)
646    {
647        str += "max(";
648        t1.prettyPrint(str, format);
649        str += ",";
650        t2.prettyPrint(str, format);
651        str += ")";
652    }
653};
654
655BZ_NAMESPACE_END
656
657#endif // BZ_FUNCS_H
Note: See TracBrowser for help on using the repository browser.