]> www.ginac.de Git - ginac.git/blobdiff - ginac/inifcns_nstdsums.cpp
G_numeric: fix numeric evaluation with trailing zeros and y != 1.
[ginac.git] / ginac / inifcns_nstdsums.cpp
index 9876075c6526fdd4fd6983cc5a37798ca3179eb2..62c6c62f2737cf6b87a34db73bc51060103c1ff5 100644 (file)
@@ -1136,6 +1136,7 @@ G_numeric(const std::vector<cln::cl_N>& x, const std::vector<int>& s,
        // check for convergence and necessary accelerations
        bool need_trafo = false;
        bool need_hoelder = false;
+       bool have_trailing_zero = false;
        std::size_t depth = 0;
        for (std::size_t i = 0; i < x.size(); ++i) {
                if (!zerop(x[i])) {
@@ -1149,14 +1150,16 @@ G_numeric(const std::vector<cln::cl_N>& x, const std::vector<int>& s,
                                need_hoelder = true;
                }
        }
-       if (zerop(x[x.size() - 1]))
+       if (zerop(x[x.size() - 1])) {
+               have_trailing_zero = true;
                need_trafo = true;
+       }
 
        if (depth == 1 && x.size() == 2 && !need_trafo)
                return - Li_projection(2, y/x[1], cln::float_format(Digits));
        
        // do acceleration transformation (hoelder convolution [BBB])
-       if (need_hoelder)
+       if (need_hoelder && !have_trailing_zero)
                return G_do_hoelder(x, s, y);
        
        // convergence transformation
@@ -1577,7 +1580,17 @@ static ex Li_eval(const ex& m_, const ex& x_)
                                }
                        }
                        if (is_zeta) {
-                               return zeta(m_,x_);
+                               lst newx;
+                               for (lst::const_iterator itx = x.begin(); itx != x.end(); ++itx) {
+                                       GINAC_ASSERT((*itx == _ex1) || (*itx == _ex_1));
+                                       // XXX: 1 + 0.0*I is considered equal to 1. However
+                                       // the former is a not automatically converted
+                                       // to a real number. Do the conversion explicitly
+                                       // to avoid the "numeric::operator>(): complex inequality"
+                                       // exception (and similar problems).
+                                       newx.append(*itx != _ex_1 ? _ex1 : _ex_1);
+                               }
+                               return zeta(m_, newx);
                        }
                        if (is_H) {
                                ex prefactor;
@@ -2494,7 +2507,12 @@ lst convert_parameter_Li_to_H(const lst& m, const lst& x, ex& pf)
        res.append(*itm);
        itm++;
        while (itx != x.end()) {
-               signum *= (*itx > 0) ? 1 : -1;
+               GINAC_ASSERT((*itx == _ex1) || (*itx == _ex_1));
+               // XXX: 1 + 0.0*I is considered equal to 1. However the former
+               // is not automatically converted to a real number.
+               // Do the conversion explicitly to avoid the
+               // "numeric::operator>(): complex inequality" exception.
+               signum *= (*itx != _ex_1) ? 1 : -1;
                pf *= signum;
                res.append((*itm) * signum);
                itm++;