* functions. */
/*
- * GiNaC Copyright (C) 1999-2001 Johannes Gutenberg University Mainz, Germany
+ * GiNaC Copyright (C) 1999-2003 Johannes Gutenberg University Mainz, Germany
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
#include "constant.h"
#include "numeric.h"
#include "power.h"
+#include "operators.h"
#include "relational.h"
#include "symbol.h"
#include "pseries.h"
// exp(n*Pi*I/2) -> {+1|+I|-1|-I}
const ex TwoExOverPiI=(_ex2*x)/(Pi*I);
if (TwoExOverPiI.info(info_flags::integer)) {
- numeric z = mod(ex_to<numeric>(TwoExOverPiI),_num4);
+ const numeric z = mod(ex_to<numeric>(TwoExOverPiI),_num4);
if (z.is_equal(_num0))
return _ex1;
if (z.is_equal(_num1))
}
// log(exp(t)) -> t (if -Pi < t.imag() <= Pi):
if (is_ex_the_function(x, exp)) {
- ex t = x.op(0);
+ const ex &t = x.op(0);
if (t.info(info_flags::numeric)) {
- numeric nt = ex_to<numeric>(t);
+ const numeric &nt = ex_to<numeric>(t);
if (nt.is_real())
return t;
}
int order,
unsigned options)
{
- GINAC_ASSERT(is_exactly_a<symbol>(rel.lhs()));
+ GINAC_ASSERT(is_a<symbol>(rel.lhs()));
ex arg_pt;
bool must_expand_arg = false;
// maybe substitution of rel into arg fails because of a pole
try {
- arg_pt = arg.subs(rel);
+ arg_pt = arg.subs(rel, subs_options::no_pattern);
} catch (pole_error) {
must_expand_arg = true;
}
} while (!argser.is_terminating() && argser.nops()==1);
const symbol &s = ex_to<symbol>(rel.lhs());
- const ex point = rel.rhs();
+ const ex &point = rel.rhs();
const int n = argser.ldegree(s);
epvector seq;
// construct what we carelessly called the n*log(x) term above
// This is the branch cut: assemble the primitive series manually and
// then add the corresponding complex step function.
const symbol &s = ex_to<symbol>(rel.lhs());
- const ex point = rel.rhs();
+ const ex &point = rel.rhs();
const symbol foo;
- const ex replarg = series(log(arg), s==foo, order).subs(foo==point);
+ const ex replarg = series(log(arg), s==foo, order).subs(foo==point, subs_options::no_pattern);
epvector seq;
seq.push_back(expair(-I*csgn(arg*I)*Pi, _ex0));
seq.push_back(expair(Order(_ex1), order));
}
if (is_exactly_a<function>(x)) {
- ex t = x.op(0);
+ const ex &t = x.op(0);
// sin(asin(x)) -> x
if (is_ex_the_function(x, asin))
return t;
}
if (is_exactly_a<function>(x)) {
- ex t = x.op(0);
+ const ex &t = x.op(0);
// cos(acos(x)) -> x
if (is_ex_the_function(x, acos))
return t;
}
if (is_exactly_a<function>(x)) {
- ex t = x.op(0);
+ const ex &t = x.op(0);
// tan(atan(x)) -> x
if (is_ex_the_function(x, atan))
return t;
int order,
unsigned options)
{
- GINAC_ASSERT(is_exactly_a<symbol>(rel.lhs()));
+ GINAC_ASSERT(is_a<symbol>(rel.lhs()));
// method:
// Taylor series where there is no pole falls back to tan_deriv.
// On a pole simply expand sin(x)/cos(x).
- const ex x_pt = x.subs(rel);
+ const ex x_pt = x.subs(rel, subs_options::no_pattern);
if (!(2*x_pt/Pi).info(info_flags::odd))
throw do_taylor(); // caught by function::series()
// if we got here we have to care for a simple pole
int order,
unsigned options)
{
- GINAC_ASSERT(is_exactly_a<symbol>(rel.lhs()));
+ GINAC_ASSERT(is_a<symbol>(rel.lhs()));
// method:
// Taylor series where there is no pole or cut falls back to atan_deriv.
// There are two branch cuts, one runnig from I up the imaginary axis and
// On the branch cuts and the poles series expand
// (log(1+I*x)-log(1-I*x))/(2*I)
// instead.
- const ex arg_pt = arg.subs(rel);
+ const ex arg_pt = arg.subs(rel, subs_options::no_pattern);
if (!(I*arg_pt).info(info_flags::real))
throw do_taylor(); // Re(x) != 0
if ((I*arg_pt).info(info_flags::real) && abs(I*arg_pt)<_ex1)
// This is the branch cut: assemble the primitive series manually and
// then add the corresponding complex step function.
const symbol &s = ex_to<symbol>(rel.lhs());
- const ex point = rel.rhs();
+ const ex &point = rel.rhs();
const symbol foo;
- const ex replarg = series(atan(arg), s==foo, order).subs(foo==point);
+ const ex replarg = series(atan(arg), s==foo, order).subs(foo==point, subs_options::no_pattern);
ex Order0correction = replarg.op(0)+csgn(arg)*Pi*_ex_1_2;
if ((I*arg_pt)<_ex0)
Order0correction += log((I*arg_pt+_ex_1)/(I*arg_pt+_ex1))*I*_ex_1_2;
return I*sin(x/I);
if (is_exactly_a<function>(x)) {
- ex t = x.op(0);
+ const ex &t = x.op(0);
// sinh(asinh(x)) -> x
if (is_ex_the_function(x, asinh))
return t;
return cos(x/I);
if (is_exactly_a<function>(x)) {
- ex t = x.op(0);
+ const ex &t = x.op(0);
// cosh(acosh(x)) -> x
if (is_ex_the_function(x, acosh))
return t;
return I*tan(x/I);
if (is_exactly_a<function>(x)) {
- ex t = x.op(0);
+ const ex &t = x.op(0);
// tanh(atanh(x)) -> x
if (is_ex_the_function(x, atanh))
return t;
int order,
unsigned options)
{
- GINAC_ASSERT(is_exactly_a<symbol>(rel.lhs()));
+ GINAC_ASSERT(is_a<symbol>(rel.lhs()));
// method:
// Taylor series where there is no pole falls back to tanh_deriv.
// On a pole simply expand sinh(x)/cosh(x).
- const ex x_pt = x.subs(rel);
+ const ex x_pt = x.subs(rel, subs_options::no_pattern);
if (!(2*I*x_pt/Pi).info(info_flags::odd))
throw do_taylor(); // caught by function::series()
// if we got here we have to care for a simple pole
int order,
unsigned options)
{
- GINAC_ASSERT(is_exactly_a<symbol>(rel.lhs()));
+ GINAC_ASSERT(is_a<symbol>(rel.lhs()));
// method:
// Taylor series where there is no pole or cut falls back to atanh_deriv.
// There are two branch cuts, one runnig from 1 up the real axis and one
// On the branch cuts and the poles series expand
// (log(1+x)-log(1-x))/2
// instead.
- const ex arg_pt = arg.subs(rel);
+ const ex arg_pt = arg.subs(rel, subs_options::no_pattern);
if (!(arg_pt).info(info_flags::real))
throw do_taylor(); // Im(x) != 0
if ((arg_pt).info(info_flags::real) && abs(arg_pt)<_ex1)
// This is the branch cut: assemble the primitive series manually and
// then add the corresponding complex step function.
const symbol &s = ex_to<symbol>(rel.lhs());
- const ex point = rel.rhs();
+ const ex &point = rel.rhs();
const symbol foo;
- const ex replarg = series(atanh(arg), s==foo, order).subs(foo==point);
+ const ex replarg = series(atanh(arg), s==foo, order).subs(foo==point, subs_options::no_pattern);
ex Order0correction = replarg.op(0)+csgn(I*arg)*Pi*I*_ex1_2;
if (arg_pt<_ex0)
Order0correction += log((arg_pt+_ex_1)/(arg_pt+_ex1))*_ex1_2;