int main(int argc,char **argv) { if(argc!=2) { printf("[USAGE] %s [lint]\n",*argv); exit(-1); } lint *n=convertI(*(argv+1)),*fibo=_fibonacciI(n); printI(n); printf("F="); printI(fibo); printf("\n"); deleteI(n); deleteI(fibo); return 0; }
//returns new lint with product of lint a and b, assumed trimmed and +ve with a>b lint *_multiplicationI(lint *a,lint *b) { lint *prod=createI(a->length),*tmp1,*tmp2,*tmp3,*tmp4; int i; for(i=b->length-1;i>=0;--i) { tmp1=shiftI(prod,1); tmp2=intoI(a,b->digits[i]); tmp3=_additionI(tmp1,tmp2); tmp4=shrinkI(tmp3); deleteI(prod); deleteI(tmp3); deleteI(tmp2); deleteI(tmp1); prod=tmp4; } return prod; }
Automate::~Automate(){ deleteTableTranstion(); deleteQ(); deleteI(); deleteT(); }
//returns new lint with lint a to the power b, assumed trimmed lint *powerI(lint *a,lint *b) { if(b->sign==MINUS) return createI(1); if(a->sign==PLUS) return _powerI(a,b); lint *one=convertI("1"),*two=convertI("2"),**div=_divisionI(b,two); switch(_compareI(*(div+1),one)) { case LESS: destroyI(div,2); deleteI(one); deleteI(two); return _powerI(a,b); case EQUAL: destroyI(div,2); deleteI(one); deleteI(two); return negateI(_powerI(a,b)); } }
//returns new lint with lint a to the power b, assumed trimmed and +ve lint *_powerI(lint *a,lint *b) { lint *one=convertI("1"),*two,*mul,**div,*pow,*tmp; switch(_compareI(b,one)) { case GREATER: two=convertI("2"); div=_divisionI(b,two); deleteI(two); switch(_compareI(*(div+1),one)) { case LESS: deleteI(one); pow=_powerI(a,*div); destroyI(div,2); mul=_kmultiplicationI(pow,pow); deleteI(pow); return mul; case EQUAL: deleteI(one); pow=_powerI(a,*div); destroyI(div,2); mul=_kmultiplicationI(pow,pow); deleteI(pow); tmp=_kmultiplicationI(mul,a); deleteI(mul); return tmp; } case EQUAL: deleteI(one); return cloneI(a); case LESS: return one; } }
int main(int argc,char *argv[]) { if(argc!=3) { printf("[USAGE] %s [string] [int]\n",argv[0]); printf("[string]:CONVERSION STRING\n"); printf("[int]:PRIME LOWER LIMIT\n"); exit(-1); } int l=atoi(argv[2]); lint *prime=inttolint(prm(l)); lint *strint=stringtolint(argv[1]); lint **split=_splitI(strint,(strint->length)/2); lint *sum=_additionI(*(split+1),*(split)); lint **rem=_divisionI(sum,prime); printf("STR_INT["); printI(strint); printf("]\n"); printf("PRIME["); printI(prime); printf("]\n"); printf("SPLIT_LOW["); printI(*(split)); printf("]\n"); printf("SPLIT_HIGH["); printI(*(split+1)); printf("]\n"); printf("SUM["); printI(sum); printf("]\n"); printf("REMAINDER["); printI(*(rem+1)); printf("]\n"); deleteI(prime); deleteI(strint); destroyI(split,2); deleteI(sum); destroyI(rem,2); return 0; }
lint *_fibonacciI(lint *n) { lint *i=convertI("2"),*a=convertI("1"),*b=convertI("1"),*c,*one=convertI("1"),*tmp; while(_compareI(i,n)==LESS) { c=_additionI(b,a); tmp=shrinkI(c); deleteI(c); c=tmp; deleteI(a); a=b; b=c; tmp=_additionI(i,one); deleteI(i); i=tmp; tmp=shrinkI(i); deleteI(i); i=tmp; } deleteI(i); deleteI(a); deleteI(one); return b; }
//returns new lint with product of lint a and b, assumed trimmed and +ve lint *_kmultiplicationI(lint *a,lint *b) { lint *tmp1=shrinkI(a),*tmp2=shrinkI(b),*tmp3,*tmp4,*tmp5; if(_compareI(tmp1,tmp2)==LESS) { tmp3=tmp2; tmp2=tmp1; tmp1=tmp3; } if(tmp2->length<KARATSUBA_SPLIT) { tmp3=_multiplicationI(tmp1,tmp2); tmp4=shrinkI(tmp3); deleteI(tmp1); deleteI(tmp2); deleteI(tmp3); return tmp4; } int l=tmp2->length/2; lint **ktmp1=_splitI(tmp1,l),**ktmp2=_splitI(tmp2,l); deleteI(tmp1); deleteI(tmp2); tmp1=_kmultiplicationI(*ktmp1,*ktmp2); tmp2=_additionI(*(ktmp1+1),*ktmp1); tmp3=_additionI(*(ktmp2+1),*ktmp2); tmp4=_kmultiplicationI(tmp2,tmp3); tmp5=_kmultiplicationI(*(ktmp1+1),*(ktmp2+1)); deleteI(tmp2); deleteI(tmp3); destroyI(ktmp1,2); destroyI(ktmp2,2); tmp2=shrinkI(tmp1); tmp3=shrinkI(tmp5); deleteI(tmp1); deleteI(tmp5); tmp1=tmp2; tmp5=tmp3; tmp2=_subtractionI(tmp4,tmp1); tmp3=_subtractionI(tmp2,tmp5); deleteI(tmp2); deleteI(tmp4); tmp2=shiftI(tmp5,2*l); tmp4=shiftI(tmp3,l); deleteI(tmp3); deleteI(tmp5); tmp3=shrinkI(tmp1); deleteI(tmp1); tmp1=tmp3; tmp3=_additionI(tmp4,tmp1); deleteI(tmp1); tmp1=shrinkI(tmp3); deleteI(tmp3); tmp3=tmp1; tmp1=_additionI(tmp2,tmp3); deleteI(tmp2); deleteI(tmp3); deleteI(tmp4); return tmp1; }
//destroys lint array n of length l void destroyI(lint **n,int l) { int i; for(i=0;i<l;++i) deleteI(*(n+i)); free(n); }
void Automate::standardisation(){ /* Standardise l'automate en ajoutant l'etat 'i' * */ list<list<string>*>::iterator iQ; // Insere l'etat i dans la liste des etats _Q.push_front(new list<string>); iQ = _Q.begin(); (*iQ)->push_back("i"); _tab[*iQ] = new list<list<string>*>[_A.size()]; // Insere les transitions de l'etat 'i' (regroupant les transitions des etats initiaux) for(iQ=++_Q.begin(); iQ!=_Q.end(); iQ++){ for(list<list<string>*>::iterator iI=_I.begin(); iI!=_I.end(); iI++){ if(((*iQ)->size() == (*iI)->size())&&(equal((*iQ)->begin(), ((*iQ)->end()), (*iI)->begin()))){ list<list<string>*>::iterator iiTab; for(unsigned int cpt=0; cpt<_A.size(); cpt++){ for(list<list<string>*>::iterator iTab=_tab[*iQ][cpt].begin(); iTab!=_tab[*iQ][cpt].end(); iTab++){ _tab[*_Q.begin()][cpt].push_back(new list<string>); iiTab =-- _tab[*_Q.begin()][cpt].end(); (*iiTab)->insert((*iiTab)->begin(),(*iTab)->begin(),(*iTab)->end()); } } } } } // Tri les transitions de l'etat 'i' iQ = _Q.begin(); for(unsigned int cpt=0; cpt<_A.size(); cpt++){ for(list<list<string>*>::iterator iTab=_tab[*iQ][cpt].begin(); iTab!=_tab[*iQ][cpt].end(); iTab++){ (*iTab)->sort(); (*iTab)->unique(); } } \ // Si un des etats initiaux est terminal int temp = 0; list<list<string>*>::iterator iI; list<list<string>*>::iterator iT; iI=_I.begin(); while ((iI != _I.end())&&(temp == 0)){ iT=_T.begin(); while ((iT != _T.end())&&(temp == 0)){ if (((*iI)->size() == (*iT)->size())&&(equal((*iI)->begin(),(*iI)->end(),(*iT)->begin()))) temp = 1; iT++; } iI++; } // Insere 'i' dans les etats terminaux if (temp == 1){ _T.push_front(new list<string>); (*_T.begin())->push_back("i"); } // Remplace les etats initiaux par 'i' deleteI(); _I.push_front(new list<string>); (*_I.begin())->push_back("i"); }
bool Automate::ouvrir(const string& nomFichier){ deleteTableTranstion(); deleteA(); deleteQ(); deleteI(); deleteT(); ifstream fichier(nomFichier.c_str(), ios::in); if (fichier.is_open()){ string charA; string charQ; string charI; string charT; string charTDT; string temp; getline(fichier,charA); for(unsigned int i = 0; i < charA.size(); i++) { temp.clear(); while ((i < charA.size())&&(charA[i] == ' ')) i++; while((i < charA.size())&&(charA[i] != ' ')){ temp += charA.substr(i,1); i++; } _A.push_back(temp); } getline(fichier,charQ); for(unsigned int i = 0; i < charQ.size(); i++) { temp.clear(); while ((i < charQ.size())&&(charQ[i] == ' ')) i++; while((i < charQ.size())&&(charQ[i] != ' ')){ temp += charQ.substr(i,1); i++; } _Q.push_back(new list<string>); (*--_Q.end())->push_back(temp); } getline(fichier,charI); for(unsigned int i = 0; i < charI.size(); i++) { temp.clear(); while ((i < charI.size())&&(charI[i] == ' ')) i++; while((i < charI.size())&&(charI[i] != ' ')){ temp += charI.substr(i,1); i++; } _I.push_back(new list<string>); (*--_I.end())->push_back(temp); } getline(fichier,charT); for(unsigned int i = 0; i < charT.size(); i++) { temp.clear(); while ((i < charT.size())&&(charT[i] == ' ')) i++; while((i < charT.size())&&(charT[i] != ' ')){ temp += charT.substr(i,1); i++; } _T.push_back(new list<string>); (*--_T.end())->push_back(temp); } list<list<string>*>::iterator iQ; for(iQ=_Q.begin(); iQ!=_Q.end(); iQ++){ _tab[*iQ]=new list<list<string>*>[_A.size()]; } getline(fichier,charTDT); iQ = _Q.begin(); unsigned int col; unsigned int start; while ((!fichier.eof())&&(iQ != _Q.end())){ getline(fichier,charTDT); col = 0; start = 0; while ((start < charTDT.size())&&(charTDT[start] == ' ')) start++; while(charTDT[start] != ' ') start++; for(unsigned int i=start; i < charTDT.size(); i++){ temp.clear(); while ((i < charTDT.size())&&(charTDT[i] == ' ')) i++; while((i < charTDT.size())&&(charTDT[i] != ',')&&(charTDT[i] != ' ')){ temp += charTDT.substr(i,1); i++; } if (temp != "-"){ _tab[*iQ][col].push_back(new list<string>); (*--_tab[*iQ][col].end())->push_back(temp); } if (charTDT[i] == ','){ i++; } else{ col++; } } iQ++; } return true; } return false; }
bool Automate::minimiser(){ /* Minimise l'automate * Retourne true si l'automate etait deja minimal <=> Le nombre de groupe cree lors de la minimisation est egal au nombre d'etat de l'automate * Retourne false si l'automate n'etait pas minimal * */ list<string> groupes; // La liste des groupes Ex : {NT, T} list<string> tempgroupes; // Une liste des groupes temporaires string groupeString; // Le groupe auquel appartient un etat map<string, list<list<string>*>*> tabG; // Un tableau indexe par les groupes contenant la liste des etats dans un groupe //Initialisation de tempGroupes et de tabG tempgroupes.push_back("NT"); tempgroupes.push_back("T"); tabG["NT"] = new list<list<string>*>; tabG["T"] = new list<list<string>*>; for(list<list<string>*>::iterator iQ=_T.begin(); iQ!=_T.end(); iQ++) tabG["T"]->push_back(*iQ); for(list<list<string>*>::iterator iQ=_Q.begin(); iQ!=_Q.end(); iQ++){ int temp = 0; for(list<list<string>*>::iterator iT=_T.begin(); iT!=_T.end(); iT++){ if( ((*iT)->size() == (*iQ)->size()) && (equal( (*iQ)->begin(), (*iQ)->end(), (*iT)->begin()) )){ temp = 1; } } if(temp == 0) tabG["NT"]->push_back(*iQ); } list<string>::iterator iG; QStringList liste; QString tempS; int cptG; // Tant que le nombre de groupe n'est pas egal a celui de la derniere iteration while (groupes.size() != tempgroupes.size()) { // Initialisation de groupes et reinitialisation de tempgroupes groupes = tempgroupes; tempgroupes.clear(); cptG = 1; for(list<string>::iterator i = groupes.begin(); i != groupes.end(); i++){ tempS.clear(); tempS += "Group " + QString::number(cptG) + " : "; for(list<list<string>*>::iterator ii = tabG[*i]->begin(); ii != tabG[*i]->end(); ii++){ if (ii != tabG[*i]->begin()) tempS += ", "; tempS += "{"; for(list<string>::iterator iii = (*ii)->begin(); iii != (*ii)->end(); iii++){ if(iii != (*ii)->begin()) tempS += ", "; tempS += QString::fromStdString(*iii); } tempS += "}"; } liste << tempS; cptG++; } liste << ""; // Pour chaque etat for(list<list<string>*>::iterator iQ=_Q.begin(); iQ!=_Q.end(); iQ++){ // Reinitialisation de groupeString groupeString.clear(); iG = groupes.begin(); int temp; // Faire tant que nous ne trouvons pas dans quel groupe est cet etat temp = 1; do { for(list<list<string>*>::iterator iiG = tabG[*iG]->begin(); iiG != tabG[*iG]->end(); iiG++){ // Si les etats sont egaux if (((*iiG)->size() == (*iQ)->size())&&(equal((*iiG)->begin(), (*iiG)->end(), (*iQ)->begin()))) temp = 0; } iG++; }while(temp == 1); iG--; // Insertion de ce groupe dans groupeString groupeString = groupeString + *iG; for (unsigned int cpt = 0; cpt != _A.size(); cpt++){ int temp; iG = groupes.begin(); temp = 1; do{ list<list<string>*>::iterator iTab = _tab[*iQ][cpt].begin(); for(list<list<string>*>::iterator iiG = tabG[*iG]->begin(); iiG != tabG[*iG]->end(); iiG++){ if (((*iiG)->size() == (*iTab)->size())&&(equal((*iiG)->begin(), (*iiG)->end(), (*iTab)->begin()))) // Si les etats ne sont pas egaux temp = 0; } iG++; }while(temp == 1); iG--; // Insertion de ce groupe dans groupeString groupeString = groupeString + *iG; } if(tabG[groupeString] == NULL){ tabG[groupeString] = new list<list<string>*>; } // Insertion de cet etat dans son groupe tabG[groupeString]->push_back(*iQ); tempgroupes.push_back(groupeString); tempgroupes.sort(); tempgroupes.unique(); } // Suppression des anciens groupes for (list<string>::iterator it=groupes.begin(); it != groupes.end(); it++) tabG[*it]->clear(); } Interface::messageMinimiser(&liste); groupes = tempgroupes; tempgroupes.clear(); if(groupes.size() == _Q.size()) return true; list<list<string>*> Qmin, Tmin, Imin; list<string>::iterator iGG; list<list<string>*>::iterator iTabG; list<list<string>*>::iterator iTab; int temp; list<list<string>*>::iterator iI; list<list<string>*>::iterator iIm; iI = _I.begin(); iG=groupes.begin(); temp = 1; do { for(list<list<string>*>::iterator iiG = tabG[*iG]->begin(); iiG != tabG[*iG]->end(); iiG++){ if (((*iiG)->size() == (*iI)->size())&&(equal((*iiG)->begin(), (*iiG)->end(), (*iI)->begin()))) // Si les etats ne sont pas egaux temp = 0; } iG++; }while(temp == 1); iG--; Imin.push_back(new list<string>); iIm =-- Imin.end(); for(list<list<string>*>::iterator iTabGG = tabG[*iG]->begin(); iTabGG != tabG[*iG]->end(); iTabGG++) (*iIm)->insert(--(*iIm)->end(), (*iTabGG)->begin(), (*iTabGG)->end()); deleteI(); _I = Imin; list<list<string>*>::iterator iTmin; for(list<string>::iterator iG = groupes.begin(); iG != groupes.end(); iG++){ if ((*iG).at(0) == 'T'){ Tmin.push_back(new list<string>); iTmin =-- Tmin.end(); for(list<list<string>*>::iterator iTabG = tabG[*iG]->begin(); iTabG != tabG[*iG]->end(); iTabG++){ (*iTmin)->insert(--(*iTmin)->end(), (*iTabG)->begin(), (*iTabG)->end()); } } } deleteT(); _T = Tmin; list<list<string>*>::iterator iQmin; list<list<string>*>::iterator iTabmin; for(list<string>::iterator iG=groupes.begin(); iG != groupes.end(); iG++){ // Creation des états Qmin.push_back(new list<string>); iQmin = --Qmin.end(); for(iTabG = tabG[*iG]->begin(); iTabG != tabG[*iG]->end(); iTabG++){ (*iQmin)->insert(--(*iQmin)->end(), (*iTabG)->begin(), (*iTabG)->end()); } // Creation des transitions associes a chaque etat _tab[*(--Qmin.end())] = new list<list<string>*>[_A.size()]; // Pour chaque transition for(unsigned int cpt = 0; cpt < _A.size(); cpt++){ // Pour un etat dans le groupe iTabG = tabG[*iG]->begin(); // Pour une transition de de cet etat dans le groupe iTab = _tab[*iTabG][cpt].begin(); int temp; iGG = groupes.begin(); temp = 1; // Faire tant que nous ne trouvons pas dans quel groupe est cet etat do { for(list<list<string>*>::iterator iiG = tabG[*iGG]->begin(); iiG != tabG[*iGG]->end(); iiG++){ if (((*iiG)->size() == (*iTab)->size())&&(equal((*iiG)->begin(), (*iiG)->end(), (*iTab)->begin()))) temp = 0; } iGG++; }while(temp == 1); iGG--; _tab[*(--Qmin.end())][cpt].push_back(new list<string>); iTabmin =-- _tab[*(--Qmin.end())][cpt].end(); for(list<list<string>*>::iterator iTabGG = tabG[*iGG]->begin(); iTabGG != tabG[*iGG]->end(); iTabGG++) (*iTabmin)->insert(--(*iTabmin)->end(), (*iTabGG)->begin(), (*iTabGG)->end()); } } deleteQ(); _Q = Qmin; return false; }