Show
Ignore:
Timestamp:
03/11/07 15:11:02 (2 years ago)
Author:
pernet
Message:

New algorithm for charpoly: CharpolyArithProg?

- Complete the unfinished preconditionning phase (using complementary subspace comp. and rec. call)
- Exception management for the Las Vegas failure
- set as default for charpoly

Files:
1 modified

Legend:

Unmodified
Added
Removed
  • include/fflas-ffpack/ffpack_charpoly.inl

    r1 r3  
    1111template <class Field, class Polynomial> 
    1212std::list<Polynomial>& 
    13 FFPACK::CharPoly( const Field& F, std::list<Polynomial>& charp, const size_t N, 
    14                             typename Field::Element * A, const size_t lda, 
    15                             const enum FFPACK_CHARPOLY_TAG CharpTag ){ 
    16         switch ( CharpTag ) { 
     13FFPACK::CharPoly (const Field& F, std::list<Polynomial>& charp, const size_t N, 
     14                  typename Field::Element * A, const size_t lda, 
     15                  const enum FFPACK_CHARPOLY_TAG CharpTag){ 
     16        switch (CharpTag) { 
    1717        case FfpackLUK:{ 
    1818                typename Field::Element * X = new typename Field::Element[N*(N+1)]; 
    19                 LUKrylov( F, charp, N, A, lda, X, N); 
     19                LUKrylov (F, charp, N, A, lda, X, N); 
    2020                delete[] X; 
    2121                return charp; 
    2222        } 
    2323        case FfpackKG:{ 
    24                 return KellerGehrig( F, charp, N, A, lda ); 
     24                return KellerGehrig (F, charp, N, A, lda); 
    2525                break; 
    2626        } 
     
    3131        case FfpackKGFast:{ 
    3232                size_t mc, mb, j; 
    33                 if (KGFast( F, charp, N, A, lda, &mc, &mb, &j )){ 
     33                if (KGFast (F, charp, N, A, lda, &mc, &mb, &j)){ 
    3434                        std::cerr<<"NON GENERIC MATRIX PROVIDED TO KELLER-GEHRIG-FAST"<<std::endl; 
    3535                } 
     
    4343        case FfpackHybrid:{ 
    4444                typename Field::Element * X = new typename Field::Element[N*(N+1)]; 
    45                 LUKrylov_KGFast( F, charp, N, A, lda, X, N); 
     45                LUKrylov_KGFast (F, charp, N, A, lda, X, N); 
    4646                delete[] X; 
     47                return charp; 
     48                break; 
     49        } 
     50 
     51        case FfpackArithProg:{ 
     52                size_t attempts=0; 
     53                bool cont = false; 
     54                do{ 
     55                        try { 
     56                                CharpolyArithProg (F, charp, N, A, lda, 30); 
     57                        } 
     58                        catch (CharpolyFailed){ 
     59                                if (attempts<2) 
     60                                        cont = true; 
     61                                else 
     62                                        CharPoly(F, charp, N, A, lda, FfpackLUK); 
     63 
     64                        } 
     65                } while (cont); 
    4766                return charp; 
    4867                break; 
     
    5069        default:{ 
    5170                typename Field::Element * X = new typename Field::Element[N*(N+1)]; 
    52                 LUKrylov( F, charp, N, A, lda, X, N); 
     71                LUKrylov (F, charp, N, A, lda, X, N); 
    5372                delete[] X; 
    5473                return charp; 
     
    6079template <class Field, class Polynomial> 
    6180std::list<Polynomial>& 
    62 FFPACK::LUKrylov( const Field& F, std::list<Polynomial>& charp, const size_t N, 
    63                   typename Field::Element * A, const size_t lda, 
    64                   typename Field::Element * X, const size_t ldx){ 
     81FFPACK::LUKrylov (const Field& F, std::list<Polynomial>& charp, const size_t N, 
     82                 typename Field::Element * A, const size_t lda, 
     83                 typename Field::Element * X, const size_t ldx){ 
    6584         
    6685        typedef typename Field::Element elt; 
     
    7392        charp.clear(); 
    7493        int nbfac = 0; 
    75         while( Ncurr > 0 ){ 
     94        while (Ncurr > 0){ 
    7695                size_t P[Ncurr]; 
    77                 Polynomial minP;//=new  Polynomial(); 
    78                 MinPoly( F, minP, Ncurr, A, lda, X2, ldx, P ); 
     96                Polynomial minP;//=new Polynomial(); 
     97                MinPoly (F, minP, Ncurr, A, lda, X2, ldx, P); 
    7998                int k = minP.size()-1; // degre of minpoly 
    80                 if ( (k==1) && F.isZero( (minP)[0] ) ){ // minpoly is X 
     99                if ((k==1) && F.isZero ((minP)[0])){ // minpoly is X 
    81100                        Ai = A; 
    82101                        int j = Ncurr*Ncurr; 
    83                         while ( j-- && F.isZero(*(Ai++)) ); 
    84                         if ( !j ){ // A is 0, CharPoly=X^n 
     102                        while (j-- && F.isZero(*(Ai++))); 
     103                        if (!j){ // A is 0, CharPoly=X^n 
    85104                                minP.resize(Ncurr+1); 
    86105                                (minP)[1] = zero; 
     
    90109                } 
    91110                nbfac++; 
    92                 charp.push_front( minP ); 
    93                 if ( k==Ncurr ){ 
     111                charp.push_front (minP); 
     112                if (k==Ncurr){ 
    94113                        return charp; 
    95114                } 
     
    97116                elt * X21 = X2 + k*ldx; 
    98117                elt * X22 = X21 + k; 
    99                 //  Compute the n-k last rows of A' = PA^tP^t in X2_ 
     118                // Compute the n-k last rows of A' = PA^tP^t in X2_ 
    100119                // A = A . P^t 
    101                 applyP( F, FflasRight, FflasTrans, Ncurr, 0, k, A, lda, P); 
     120                applyP (F, FflasRight, FflasTrans, Ncurr, 0, k, A, lda, P); 
    102121                // Copy X2_ = (A'_2)^t 
    103                 for ( Xi = X21, Ai = A+k; Xi != X21 + Nrest*ldx; Ai++, Xi+=ldx-Ncurr ) 
    104                         for ( size_t jj=0; jj<Ncurr*lda; jj+=lda ) 
     122                for (Xi = X21, Ai = A+k; Xi != X21 + Nrest*ldx; Ai++, Xi+=ldx-Ncurr) 
     123                        for (size_t jj=0; jj<Ncurr*lda; jj+=lda) 
    105124                                *(Xi++) = *(Ai+jj); 
    106125                // A = A . P : Undo the permutation on A 
    107                 applyP( F, FflasRight, FflasNoTrans, Ncurr, 0, k, A, lda, P); 
    108                 // X2_ = X2_ . P^t (=  ( P A^t P^t )2_ )  
    109                 applyP( F, FflasRight, FflasTrans, Nrest, 0, k, X21, ldx, P); 
     126                applyP (F, FflasRight, FflasNoTrans, Ncurr, 0, k, A, lda, P); 
     127                // X2_ = X2_ . P^t (=  (P A^t P^t)2_)  
     128                applyP (F, FflasRight, FflasTrans, Nrest, 0, k, X21, ldx, P); 
    110129                // X21 = X21 . S1^-1 
    111130                ftrsm(F, FflasRight, FflasUpper, FflasNoTrans, FflasUnit, Nrest, k, 
    112                       one, X2, ldx, X21, ldx);   
     131                      one, X2, ldx, X21, ldx);  
    113132                // Creation of the matrix A2 for recurise call  
    114                 for ( Xi = X22, Ai = A; 
    115                       Xi != X22 + Nrest*ldx; 
    116                       Xi += (ldx-Nrest), Ai += (lda-Nrest) ) 
    117                         for ( size_t jj=0; jj<Nrest; ++jj ) 
     133                for (Xi = X22, Ai = A; 
     134                     Xi != X22 + Nrest*ldx; 
     135                     Xi += (ldx-Nrest), Ai += (lda-Nrest)) 
     136                        for (size_t jj=0; jj<Nrest; ++jj) 
    118137                                *(Ai++) = *(Xi++); 
    119                 fgemm( F, FflasNoTrans, FflasNoTrans, Nrest, Nrest, k, Mone, 
    120                        X21, ldx, X2+k, ldx, one, A, lda ); 
     138                fgemm (F, FflasNoTrans, FflasNoTrans, Nrest, Nrest, k, Mone, 
     139                       X21, ldx, X2+k, ldx, one, A, lda); 
    121140                X2 = X22; 
    122141                Ncurr = Nrest; 
     
    127146template <class Field, class Polynomial> 
    128147std::list<Polynomial>& 
    129 FFPACK::LUKrylov_KGFast( const Field& F, std::list<Polynomial>& charp, const size_t N, 
    130                                   typename Field::Element * A, const size_t lda, 
    131                                   typename Field::Element * X, const size_t ldx){ 
     148FFPACK::LUKrylov_KGFast (const Field& F, std::list<Polynomial>& charp, const size_t N, 
     149                        typename Field::Element * A, const size_t lda, 
     150                        typename Field::Element * X, const size_t ldx){ 
    132151         
    133152        typedef typename Field::Element elt; 
     
    139158        size_t kg_mc, kg_mb, kg_j; 
    140159         
    141         if (!KGFast( F, charp, N, A, lda, &kg_mc, &kg_mb, &kg_j )) 
     160        if (!KGFast (F, charp, N, A, lda, &kg_mc, &kg_mb, &kg_j)) 
    142161                return charp; 
    143162        else{// Matrix A is not generic 
     
    147166                size_t *P = new size_t[N]; 
    148167 
    149                 MinPoly( F, *minP, N, A, lda, X, ldx, P, FfpackKGF, kg_mc, kg_mb, kg_j ); 
     168                MinPoly (F, *minP, N, A, lda, X, ldx, P, FfpackKGF, kg_mc, kg_mb, kg_j); 
    150169                size_t k = minP->size()-1; // degre of minpoly 
    151                 if ( (k==1) && F.isZero( (*minP)[0] ) ){ // minpoly is X 
     170                if ((k==1) && F.isZero ((*minP)[0])){ // minpoly is X 
    152171                        Ai = A; 
    153172                        int j = N*N; 
    154                         while ( j-- && F.isZero(*(Ai++)) ); 
    155                         if ( !j ){ // A is 0, CharPoly=X^n 
     173                        while (j-- && F.isZero(*(Ai++))); 
     174                        if (!j){ // A is 0, CharPoly=X^n 
    156175                                minP->resize(N+1); 
    157176                                (*minP)[1] = zero; 
     
    161180                } 
    162181                 
    163                 if ( k==N ){ 
     182                if (k==N){ 
    164183                        charp.clear(); 
    165184                        charp.push_front(*minP); // CharPoly = MinPoly 
     
    176195                size_t imax = kg_mc+kg_mb; 
    177196                // First Id 
    178                 for ( size_t j = 0; j < lambda; ++j){ 
     197                for (size_t j = 0; j < lambda; ++j){ 
    179198                        for (size_t i=0; i<imax; ++i) 
    180                                 F.assign( *(A+j+i*lda), zero); 
    181                         F.assign( *(A+j+imax*lda), one); 
     199                                F.assign (*(A+j+i*lda), zero); 
     200                        F.assign (*(A+j+imax*lda), one); 
    182201                        for (size_t i=imax+1; i<N; ++i) 
    183                                 F.assign( *(A+j+i*lda), zero); 
     202                                F.assign (*(A+j+i*lda), zero); 
    184203                        ++imax; 
    185204                } 
    186205                // Column block B 
    187206                for (typename Field::Element* Ai=A; Ai<A+N*lda; Ai+=lda) 
    188                         fcopy( F, kg_mb, Ai+lambda, 1, Ai+N-kg_mc-kg_mb, 1 ); 
     207                        fcopy (F, kg_mb, Ai+lambda, 1, Ai+N-kg_mc-kg_mb, 1); 
    189208 
    190209                // Second Id block 
     
    192211                for (size_t j = 0; j< kg_j*kg_mc; ++j){ 
    193212                        for (size_t i = 0; i<imax; ++i) 
    194                                 F.assign( *(A+lambda+kg_mb+j+i*lda), zero ); 
    195                         F.assign( *(A+lambda+kg_mb+j+imax*lda), one ); 
     213                                F.assign (*(A+lambda+kg_mb+j+i*lda), zero); 
     214                        F.assign (*(A+lambda+kg_mb+j+imax*lda), one); 
    196215                        for (size_t i = imax+1; i<N; ++i) 
    197                                 F.assign( *(A+lambda+kg_mb+j+i*lda), zero ); 
     216                                F.assign (*(A+lambda+kg_mb+j+i*lda), zero); 
    198217                        ++imax; 
    199218                } 
    200219                 
    201                 //  Compute the n-k last rows of A' = PA^tP^t in X2_ 
     220                // Compute the n-k last rows of A' = PA^tP^t in X2_ 
    202221                 
    203222                // A = P . A  
    204                 applyP( F, FflasLeft, FflasNoTrans, N, 0, k,  
     223                applyP (F, FflasLeft, FflasNoTrans, N, 0, k,  
    205224                        const_cast<typename Field::Element* &>(A), lda, P); 
    206225                 
    207226                // Copy X2_ = (A'2_) 
    208                 for ( Xi = X21, Ai = A+k*lda; Xi != X21 + Nrest*ldx; Ai+=lda-N, Xi+=ldx-N ){ 
    209                         for ( size_t jj=0; jj<N; ++jj ){ 
     227                for (Xi = X21, Ai = A+k*lda; Xi != X21 + Nrest*ldx; Ai+=lda-N, Xi+=ldx-N){ 
     228                        for (size_t jj=0; jj<N; ++jj){ 
    210229                                *(Xi++) = *(Ai++); 
    211230                        } 
     
    213232 
    214233                // A = P^t . A : Undo the permutation on A 
    215                 applyP( F, FflasLeft, FflasTrans, N, 0, k,  
     234                applyP (F, FflasLeft, FflasTrans, N, 0, k,  
    216235                        const_cast<typename Field::Element* &>(A), lda, P); 
    217236         
    218                 // X2_ = X2_ . P^t (=  ( P A P^t )2_ )  
    219                 applyP( F, FflasRight, FflasTrans, Nrest, 0, k, X21, ldx, P); 
     237                // X2_ = X2_ . P^t (=  (P A P^t)2_)  
     238                applyP (F, FflasRight, FflasTrans, Nrest, 0, k, X21, ldx, P); 
    220239 
    221240                // X21 = X21 . S1^-1 
     
    226245                elt * A2 = new elt[Nrest*Nrest]; 
    227246         
    228                 for ( Xi = X22, A2i = A2; 
    229                       Xi != X22 + Nrest*ldx; 
    230                       Xi += (ldx-Nrest) ){ 
    231                         for ( size_t jj=0; jj<Nrest; ++jj ){ 
     247                for (Xi = X22, A2i = A2; 
     248                     Xi != X22 + Nrest*ldx; 
     249                     Xi += (ldx-Nrest)){ 
     250                        for (size_t jj=0; jj<Nrest; ++jj){ 
    232251                                *(A2i++) = *(Xi++); 
    233252                        } 
    234253                } 
    235                 fgemm( F, FflasNoTrans, FflasNoTrans, Nrest, Nrest, k, Mone, 
    236                        X21, ldx, X+k, ldx, one, A2, Nrest ); 
     254                fgemm (F, FflasNoTrans, FflasNoTrans, Nrest, Nrest, k, Mone, 
     255                       X21, ldx, X+k, ldx, one, A2, Nrest); 
    237256         
    238257                // Recursive call on X22 
    239                 LUKrylov_KGFast( F, charp, Nrest, A2, Nrest, X22, ldx ); 
    240                 charp.push_front( *minP ); 
     258                LUKrylov_KGFast (F, charp, Nrest, A2, Nrest, X22, ldx); 
     259                charp.push_front (*minP); 
    241260                delete[] P; 
    242261                delete[] A2;