]> www.ginac.de Git - ginac.git/blobdiff - ginac/factor.cpp
Fixed bug in the Q matrix calculation and the univariate factorization function.
[ginac.git] / ginac / factor.cpp
index 18e7c04c78bc3ce86dab49e377f7a25de44d0aa3..5489b4ceb79eb87a99ba36ef9e17e5dac96b3005 100644 (file)
@@ -700,19 +700,32 @@ static void q_matrix(const UniPoly& a, Matrix& Q)
 {
        unsigned int n = a.degree();
        unsigned int q = cl_I_to_uint(a.R->modulus);
-       vector<cl_MI> r(n, a.R->zero());
-       r[0] = a.R->one();
-       Q.set_row(0, r);
-       unsigned int max = (n-1) * q;
-       for ( size_t m=1; m<=max; ++m ) {
-               cl_MI rn_1 = r.back();
-               for ( size_t i=n-1; i>0; --i ) {
-                       r[i] = r[i-1] - rn_1 * a[i];
-               }
-               r[0] = -rn_1 * a[0];
-               if ( (m % q) == 0 ) {
-                       Q.set_row(m/q, r);
+// fast and buggy
+//     vector<cl_MI> r(n, a.R->zero());
+//     r[0] = a.R->one();
+//     Q.set_row(0, r);
+//     unsigned int max = (n-1) * q;
+//     for ( size_t m=1; m<=max; ++m ) {
+//             cl_MI rn_1 = r.back();
+//             for ( size_t i=n-1; i>0; --i ) {
+//                     r[i] = r[i-1] - rn_1 * a[i];
+//             }
+//             r[0] = -rn_1 * a[0];
+//             if ( (m % q) == 0 ) {
+//                     Q.set_row(m/q, r);
+//             }
+//     }
+// slow and (hopefully) correct
+       for ( size_t i=0; i<n; ++i ) {
+               UniPoly qk(a.R);
+               qk.set(i*q, a.R->one());
+               UniPoly r(a.R);
+               rem(qk, a, r);
+               Vec rvec;
+               for ( size_t j=0; j<n; ++j ) {
+                       rvec.push_back(r[j]);
                }
+               Q.set_row(i, rvec);
        }
 }
 
@@ -795,7 +808,12 @@ static void berlekamp(const UniPoly& a, UniPolyVec& upv)
                                        *u = uo;
                                }
                                factors.push_back(g);
-                               ++size;
+                               size = 0;
+                               list<UniPoly>::const_iterator i = factors.begin(), end = factors.end();
+                               while ( i != end ) {
+                                       if ( i->degree() ) ++size; 
+                                       ++i;
+                               }
                                if ( size == k ) {
                                        list<UniPoly>::const_iterator i = factors.begin(), end = factors.end();
                                        while ( i != end ) {
@@ -803,9 +821,9 @@ static void berlekamp(const UniPoly& a, UniPolyVec& upv)
                                        }
                                        return;
                                }
-                               if ( u->degree() < nur.degree() ) {
-                                       break;
-                               }
+//                             if ( u->degree() < nur.degree() ) {
+//                                     break;
+//                             }
                        }
                }
                if ( ++r == k ) {
@@ -1107,6 +1125,7 @@ static ex factor_univariate(const ex& poly, const ex& x)
                                        mf.factors = newfactors2;
                                        mf.poly = answer.op(1);
                                        tocheck.push(mf);
+                                       break;
                                }
                        }
                        else {