예제 #1
0
void CommandeSqr::execute()throw(LogMessage){
    savePileAvtExe();
    Constante * c;
    try{
        c =_pileCourante->depiler();
        if(typeid(*c)!=typeid(Complexe) && typeid(*c)!=typeid(Expression)){
            //clone la constante pour pas la modifier et empiler la rempiler la mauvaise version s'il y a un problème
            Constante* clone = c->clone();
            Nombre * nbClone = dynamic_cast<Nombre*>(clone);
            nbClone->sqr_();
            if(empilerNombre(nbClone))
                savePileApresExe();
            else
                _pileCourante->empilerConstante(c);
        }
        else if(typeid(*c)==typeid(Complexe)){
            Constante* clone = c->clone();
            Complexe* coClone = dynamic_cast<Complexe*>(clone);
            coClone->sqr();
            if(empilerComplexe(coClone))
                savePileApresExe();
            else
                _pileCourante->empilerConstante(c);
        }
        else{
            _pileCourante->empilerConstante(c);
            throw LogMessage("Impossible de faire un carré sur une Expression, Il faut d'abord l'évaluer",1);
        }
    }
    catch(LogMessage &msg){
        throw;
    }
}
예제 #2
0
Element* Calculateur::inv()
{
    if(typeid(*this->pileC->top()) == typeid(Expression))
    {
         throw std::logic_error("L'élément du haut de la pile est une expression");
    }
    if(typeid(*this->pileC->top()) == typeid(Complexe))
    {
         throw std::logic_error("L'inverse d'un complexe n'est pas une commande disponible");
    }

    Constante* c = dynamic_cast<Constante *>(this->pileC->pop());
    Element* res;
    if(typeid(*c)== typeid(Entier) || typeid(*c)== typeid(Rationnel))
    {

        res = new Rationnel(c->getYAsInt(),c->getXAsInt());

    }
    else
    {
        res = new Reel(1./c->getXAsFloat());

    }

        delete c;
        this->pileC->push(res);
        return res;
}
예제 #3
0
Constante* Pile::dupliquer()
{
    Constante* temp = p.top();
    string s = temp->getChaine();

    if(temp == NULL) return NULL;

    if(temp->getType() == entier)
    {
        Entier* Dup = new Entier(s);
        return Dup;
    }
    else if(temp->getType() == rationnel)
    {
        Rationnel* Dup = new Rationnel(s);
        return Dup;
    }
    else if(temp->getType() == reel)
    {
        Reel* Dup = new Reel(s);
        return Dup;
    }
    else
    {
        Complexe* temp2 = dynamic_cast<Complexe*>(temp);
        Complexe* Dup = new Complexe(s, temp2->getContient());
        return Dup;
    }
}
void CalculatriceModele::getMean(int type){
    if(pile.size()>=1){
        Constante* a = pile.pop();
        if(typeid (*a).name()==typeid (Entier).name()){
            Entier* e = dynamic_cast<Entier*>(a);

            if(pile.size()>=e->GetEntier())
            {
                Rationnel nb_moyenne = e->inv();

                pile.push(e);
                emit getSum(type);

                a = pile.pop();
                Constante* res = nb_moyenne * a;
                qDebug()<<"res :"<<res->ConvertChaine();
                pile.push(res);
            }
            else{
                pile.push(a);
                logger1->Write(&LogMessage(ERROR,"taille pile insuffisante"));
                logger2->Write(&LogMessage(ERROR,"taille pile insuffisante"));
            }
        }
        else{
        logger1->Write(&LogMessage(ERROR,"type non conforme"));
        logger2->Write(&LogMessage(ERROR,"type non conforme"));
        }
        emit finOp(&pile);
    }
    else{
    logger1->Write(&LogMessage(ERROR,"taille pile insuffisante"));
    logger2->Write(&LogMessage(ERROR,"taille pile insuffisante"));
    }
}
예제 #5
0
bool Inferieur::application(const Constante& c1, const Constante& c2){

    bool result;
    if(c1.getType() > c2.getType()){
            result = c1<c2;
    }
    else{
            result = c2<c1;
    }
    return result;
}
예제 #6
0
bool Egal::application(const Constante& c1, const Constante& c2){

    bool result;
    if(c1.getType() > c2.getType()){
            result = c1==c2;
    }
    else{
            result = c2==c1;
    }
    return result;
}
예제 #7
0
void Pile::afficher(int tailleMax){
    QString txt = "";
    int j = 0;
    for ( int i = size() - 1; i >=0; i-- )
    {
    j++;
    if(j>tailleMax)
        break;

        Constante * c = at(i);
        txt+=c->getValuetoString();
        if(i<size())
            txt+= " | ";
    }
     affichage->setText("Pile : |" + txt);
}
예제 #8
0
Element* Calculateur::log()
{
                if(typeid(*this->pileC->top()) == typeid(Expression))
    {
    this->eval();
    }
    if(typeid(*this->pileC->top()) == typeid(Complexe))
    {
    //
    }
    if(isRadian())
    {
    Constante* tmp = dynamic_cast<Constante*> (this->pileC->pop());
        if(tmp->getXAsFloat()<0 && tmp->getYAsFloat() <0)
        {
            //ERREUR
            return 0;
        }
        else
        {
            Reel* resu = new Reel(::log10(tmp->getXAsFloat()/tmp->getYAsFloat()));
            delete tmp;
            this->pileC->push(resu);
            return resu;
        }
    }
    else
    {
        Constante* tmp = dynamic_cast<Constante*> (this->pileC->pop());
        if(tmp->getXAsFloat()<0 && tmp->getYAsFloat() <0)
            {
                //ERREUR
                return 0;
            }
        else
        {
            Reel* resu = new Reel(::log10((tmp->getXAsFloat()/tmp->getYAsFloat())));
            delete tmp;
            this->pileC->push(resu);
            return resu;
        }
    }

}
예제 #9
0
Element* Calculateur::tanh()
{
        if(typeid(*this->pileC->top()) == typeid(Expression))
    {
    this->eval();
    }
    if(typeid(*this->pileC->top()) == typeid(Complexe))
    {
    //
    }
    if(isRadian())
    {
    Constante* tmp = dynamic_cast<Constante*> (this->pileC->pop());
    Reel* resu = new Reel(::tanh(tmp->getXAsFloat()/tmp->getYAsFloat()));
    delete tmp;
    this->pileC->push(resu);
    return resu;
    }
    else
    {
    Constante* tmp = dynamic_cast<Constante*> (this->pileC->pop());
    Reel* resu = new Reel(::tanh((tmp->getXAsFloat()/tmp->getYAsFloat())*PI/180.0));
    delete tmp;
    this->pileC->push(resu);
    return resu;

    }
}
void main() {
	Contexto contexto;

	// Declaracion de Variables
	Variable *x = new Variable("x");
	Variable *y = new Variable("y");

	// Asignacion de variables
	contexto.asignar(x, 8);
	contexto.asignar(y, 4);

	// Declaracion de constantes
	Constante *constante = new Constante(2);

	// Operacion compuesta (constante * x) + (y / constante)
	E *operacion = new Suma(new Multiplica(constante, x), new Divide(y, constante));

	// Operaciones de E
	E *eSuma = new Suma(x, y);
	E *eResta = new Resta(x, y);

	// Operaciones de T
	T *tMultiplica = new Multiplica(x, y);
	T *tDivide = new Divide(x, y);

	cout<< "Valor Variable x = " << contexto.getValor("x") << endl;
	cout<< "Valor Variable y = " << contexto.getValor("y") << endl;
	cout<< "Valor Constante = " << constante->getValor(contexto) << endl;
	cout<< endl;

	cout<< "Suma: " << eSuma->getValor(contexto) << endl;
	cout<< "Resta: " << eResta->getValor(contexto) << endl;
	cout<< "Multiplicacion: " << tMultiplica->getValor(contexto) << endl;
	cout<< "Division: " << tDivide->getValor(contexto) << endl;
	cout<< "Operacion compuesta: " << operacion->getValor(contexto) << endl;

	delete x;
	delete y;
}
예제 #11
0
void CommandeLn::execute()throw(LogMessage){
    savePileAvtExe();
    Constante * c;
    try{
        c=_pileCourante->depiler();
        if(typeid(*c)!=typeid(Complexe) && typeid(*c)!=typeid(Expression)){
            //clone la constante pour pas la modifier et empiler la rempiler la mauvaise version s'il y a un problème
            Constante* clone = c->clone();
            Nombre * n = dynamic_cast<Nombre*>(clone);
            n->ln_();
            if(empilerNombre(n))
                savePileApresExe();
            else
                _pileCourante->empilerConstante(c);
        }
        else{
            _pileCourante->empilerConstante(c);
            throw LogMessage("Impossible de faire un logarithme neperien sur un Complexe ou une Expression",1);
        }
    }
    catch(LogMessage &msg){
        throw;
    }
}
예제 #12
0
/*!
  * bool operator<(const Constante& c) const
  * \brief operator<
  * Methode vérifiant si l'entier manipulé est inférieur à la constante passé en argument
  * Si la constante est un entier, alors on effectue l'operation adequate
  * \param c
  * \return true si l'entier manipulé est inférieur, false sinon
  */
bool Entier::operator<(const Constante & c) const
{
    switch(c.getType()){
        case Constante::ENTIER:
        {
            if(this->_entier < static_cast<const Entier&>(c)._entier)
            {
                return true;
            }
            else
            {
                return false;
            }
        }
    }
}
예제 #13
0
Element* Calculateur::pow()
{
    if(typeid(*this->pileC->top()) == typeid(Expression))
    {
        this->eval();
    }
    if(typeid(*this->pileC->top()) == typeid(Complexe))
    {
         throw std::logic_error("Le premier élément ne peut pas être un complexe");
    }
    else if(typeid(*this->pileC->top())== typeid(Entier))
    {
        Entier* e = dynamic_cast<Entier*>(this->pileC->pop());

        if(typeid(*this->pileC->top()) == typeid(Expression))
        {
            Element* tmp = this->eval();
        }

        else if(typeid(*this->pileC->top())== typeid(Entier) || typeid(*this->pileC->top())== typeid(Rationnel))
        {
            Constante* c = dynamic_cast<Constante*>(this->pileC->pop());

            if(e->getXAsInt()>= 0)
            {
                Rationnel* tmp = new Rationnel(::pow(c->getXAsInt(),e->getXAsInt()),::pow(c->getYAsInt(),e->getXAsInt()));
                qDebug()<<tmp->toQString();
                Element* res = this->cast(tmp);
                delete e;
                delete c;
                delete tmp;
                this->pileC->push(res);
            }
            else
            {
                Reel* tmp = new Reel(::pow(c->getXAsFloat()/c->getYAsFloat(),e->getXAsInt()));

                Element* res = this->cast(tmp);
                delete e;
                delete c;
                delete tmp;
                this->pileC->push(res);
            }
        }
        else if(typeid(*this->pileC->top()) == typeid(Reel))
        {
            Constante* c = dynamic_cast<Constante*>(this->pileC->pop());
            Reel* tmp = new Reel(::pow(c->getXAsFloat(),e->getXAsFloat()));
            Element* res = this->cast(tmp);
            delete e;
            delete c;
            delete tmp;
            this->pileC->push(res);

        }
        else
        {
         throw std::logic_error("L'élément n'est pas un type connu");
        }
    }
    else if(typeid(*this->pileC->top()) == typeid(Reel) || typeid(*this->pileC->top()) == typeid(Rationnel))
    {
        Constante* p = dynamic_cast<Constante*>(this->pileC->pop());

        if((typeid(*this->pileC->top()) == typeid(Entier))||(typeid(*this->pileC->top()) == typeid(Rationnel)) || typeid(*this->pileC->top()) == typeid(Reel))
        {
            Constante* c = dynamic_cast<Constante*>(this->pileC->pop());
            Reel* tmp = new Reel(::pow(c->getXAsFloat()/c->getYAsFloat(),p->getXAsFloat()/p->getYAsFloat()));
            Element* res = this->cast(tmp);
            delete p;
            delete c;
            delete tmp;
            this->pileC->push(res);
            return res;

        }
        else
        {
           throw std::logic_error("Le deuxième élément n'est pas un type valide");
        }
    }
    else
    {
     throw std::logic_error("Le premier élément n'est pas un élément valide");
    }

}
예제 #14
0
Constante* Eval::getValue() const {
    Expression* exp = dynamic_cast<Expression*>(c);
    QStack<Constante*> p;
    if (exp != NULL){
        int i = 0;
        QString s = exp->getExp();
        Constante * result = 0;
        while(i<s.length()){
            //on passe les espaces;
            if(s[i] == ' '){
                if(result != 0){
                    p.push(result);
                    result = 0;
                }
            }
            else if(s[i] >= '0' && s[i] <= '9'){
                if(result == 0)result = Addition(Rationnel(0),Rationnel(0),mModeConstante, mModeComplexes).getValue();
                result->addChiffre(s[i].toAscii() - '0');
            }
            else if(s[i] == '$'){
                if(result == 0) throw EvalException("$ mal placé");
                result->setDollarEntre();
            }
            else if(s[i] == '/'){
                if(result != 0){
                    result->setSlashEntre();
                }
                else{
                    if(p.size() < 2) throw EvalException("Pas assez d'opérandes pour /");
                    Constante *op2 = p.pop(),  *op1 = p.pop();
                    try{
                        result = Division(*op1,*op2,mModeConstante,mModeComplexes).getValue();
                    }
                    catch(DivException e){
                        throw EvalException("division par zéro");
                    }

                    delete op1;
                    delete op2;
                    p.push(result);
                    result = 0;
                }
            }
            else if(s[i] == ',' || s[i] == '.'){
                if(result == 0) throw EvalException(", ou . mal placé");
                result->setVirguleEntree();
            }
            else if(s[i] == '+'){
                if(result!=0){
                    p.push(result);
                    result = 0;
                }
                if(p.size() < 2) throw EvalException("Pas assez d'opérandes pour +");
                Constante *op1 = p.pop(),  *op2 = p.pop();
                result = Addition(*op1,*op2,mModeConstante,mModeComplexes).getValue();
                delete op1;
                delete op2;
                p.push(result);
                result = 0;
            }
            else if(s[i] == '-'){
                if(result!=0){
                    p.push(result);
                    result = 0;
                }
                if(p.size() < 2) throw EvalException("Pas assez d'opérandes pour -");
                Constante *op2 = p.pop(),  *op1 = p.pop();
                result = Soustraction(*op1,*op2,mModeConstante,mModeComplexes).getValue();
                delete op1;
                delete op2;
                p.push(result);
                result = 0;
            }
            else if(s[i] == '*'){
                if(result!=0){
                    p.push(result);
                    result = 0;
                }
                if(p.size() < 2) throw EvalException("Pas assez d'opérandes pour *");
                Constante *op2 = p.pop(),  *op1 = p.pop();
                result = Multiplication(*op1,*op2,mModeConstante,mModeComplexes).getValue();
                delete op1;
                delete op2;
                p.push(result);
                result = 0;
            }
            else{
                throw EvalException("Caractère inconnu");
            }
            i++;
        }
        if(result!=0)p.push(result);
        if(p.size() > 1) throw EvalException("Il manque un opérateur.");
        if(p.size() < 1) throw EvalException("Pile d'évaluation vide.");
        return p.at(0);
    }
    else throw TypeConstanteException("Ceci n'est pas une expression");
}
void OperateurPile::Execution()
{
    if (operation=="SWAP")
    {

        Constante * c1;
        Constante * c2;
        c1=Historique::GetInstance()->GetPileCalcul().Depiler();
        c2=Historique::GetInstance()->GetPileCalcul().Depiler();
        this->SWAP(c1, c2);

        QString opG=c1->ToQString();
        QString opD=c2->ToQString();


        LogSystem::GetInstance()->Publier(LogMessage("Echange de l'élément "+opG+" avec "+opD,2));
        delete c1;
        delete c2;


    }
    if (operation=="SUM")
    {
        Constante * c1=Historique::GetInstance()->GetPileCalcul().Depiler();
        Historique::GetInstance()->GetPileCalcul().Empiler(this->SUM(c1));

        QString opG=c1->ToQString();
        LogSystem::GetInstance()->Publier(LogMessage("Somme des "+opG+" premiers éléments",2));
        delete c1;

    }
    if (operation=="MEAN")
    {
        Entier * c1 =  dynamic_cast<Entier *>(Historique::GetInstance()->GetPileCalcul().Depiler());
        if (c1==NULL)
        {
            throw Exception("Erreur : Impossible de faire la moyenne d'un nombre non entier d'éléments.");
        }
        else
        {
            Constante * temp = this->SUM(c1);
            Historique::GetInstance()->GetPileCalcul().Empiler(temp->operator/(c1));
            delete temp;
            QString opG=c1->ToQString();
            LogSystem::GetInstance()->Publier(LogMessage("Moyenne des"+opG+" premiers éléments",2));
            delete c1;
        }

    }

    if (operation=="CLEAR")
    {
        /* Il faut penser à liberer la memoire quand on vide la pile*/

        PileCalcul& p=Historique::GetInstance()->GetPileCalcul();

        p.Vider();

        LogSystem::GetInstance()->Publier(LogMessage("La pile est vidée",2));



    }

    if (operation=="DUP")
    {
        Constante * temp = Historique::GetInstance()->GetPileCalcul().Depiler();
        Constante * cpy = temp->clone();
        Constante * cpy2 = temp->clone();
        delete temp;
        Historique::GetInstance()->GetPileCalcul().Empiler(cpy2);
        Historique::GetInstance()->GetPileCalcul().Empiler(cpy);

        LogSystem::GetInstance()->Publier(LogMessage("Dédoublement du premier élément de la Pile",2));
    }

    if (operation=="DROP")
    {
         delete Historique::GetInstance()->GetPileCalcul().Depiler();
        LogSystem::GetInstance()->Publier(LogMessage("Le premier élément de la pile a été effacé",2));
    }

}
예제 #16
0
// fabrique soit une constante soit un opérateur (et l'éxécute).
void Calculatrice::fabriquer(const QString& text, enumType type) const {
    Pile* p = &Pile::getInstance();
    PileAffichage* pA = &PileAffichage::getInstance();

    switch (type) {
        case ENTIER:{
            Constante* res = new Entier(text.toInt());
            p->push(res);

            // ajout log dans le fichier de log
            LogSystem::add("Push dans la pile : " + res->toString(),FAIBLE);

            // on push dans la pile d'affichage
            pA->push(text);

            break;
        }
        case REEL:{
            Constante* res = new Reel(text.toDouble());
            p->push(res);

            // ajout log dans le fichier de log
            LogSystem::add("Push dans la pile : " + res->toString(),FAIBLE);

            // on push dans la pile d'affichage
            pA->push(text);


            break;
        }
        case RATIONNEL:{
            // séparation num / den
            QStringList tmp = text.split("/");
            Constante* res = new Rationnel(tmp.value(0).toInt(), tmp.value(1).toInt());
            p->push(res);

            // ajout log dans le fichier de log
            LogSystem::add("Push dans la pile : " + res->toString(),FAIBLE);

            // on push dans la pile d'affichage
            pA->push(text);


            break;
        }
        case COMPLEXE:{
            // séparation re  $  im
            QStringList tmp = text.split("$");

            // push la partie réelle du complexe
            if (this->isEntier(tmp.value(0))) {
                this->fabriquer(tmp.value(0),ENTIER);
            } else if (this->isReel(tmp.value(0))) {
                this->fabriquer(tmp.value(0),REEL);
            } else if (this->isRationnel(tmp.value(0))) {
                this->fabriquer(tmp.value(0),RATIONNEL);
            }

            // push la partie imaginaire du complexe
            if (this->isEntier(tmp.value(1))) {
                this->fabriquer(tmp.value(1),ENTIER);
            } else if (this->isReel(tmp.value(1))) {
                this->fabriquer(tmp.value(1),REEL);
            } else if (this->isRationnel(tmp.value(1))) {
                this->fabriquer(tmp.value(1),RATIONNEL);
            }

            // pop les deux parties
            const NonComplexe* c1 = dynamic_cast<const NonComplexe*>(p->pop());
            const NonComplexe* c2 = dynamic_cast<const NonComplexe*>(p->pop());

            // construction du complexe et push.
            Complexe* res = new Complexe(*c2, *c1);
            p->push(res);

            // ajout log dans le fichier de log
            LogSystem::add("Push dans la pile : " + res->toString(),FAIBLE);

            // on push dans la pile d'affichage
            pA->push(text);

            break;

        }
        case OPERATEUR:{
            Operateur* res = new Operateur(text);

            // ajout log dans le fichier de log
            LogSystem::add("Traitement opération : " + text,FAIBLE);

            // on push dans la pile d'affichage
            pA->push(text);

            res->effectuerOperation();
            break;
        }
        case EXPRESSION:{
            QString tmp(text);
            tmp.replace(QString("'"), QString(""));
            Constante* res = new Expression(tmp);
            p->push(res);

            // ajout log dans le fichier de log
            LogSystem::add("Push dans la pile : " + res->toString(),FAIBLE);

            // on push dans la pile d'affichage
            pA->push(text);

            break;
        }
        default:{
            QMessageBox::critical(0,"Erreur !", "Fabrication d'objet impossible!");
            // ajout log dans le fichier de log
            LogSystem::add("Fabrication d'objet impossible",ELEVEE);
            break;
        }
    }
}