Number& Variable::operator/(Number& rhs) { if (typeid(rhs) == typeid(Variable)) { Variable * rhsCastVar = dynamic_cast<Variable*>(&rhs); if (rhsCastVar->var == this->var) { Number * result = new Integer(1); delete rhsCastVar; return *result; } else { std::vector<Number*> numbers; std::vector<char> operators; numbers.push_back(this); numbers.push_back(&rhs); operators.push_back('/'); Number * result = new Placeholder(numbers, operators); delete rhsCastVar; return *result; } } else if (typeid(rhs) == typeid(Exponent)) { Exponent * rhsCastExp = dynamic_cast<Exponent*>(&rhs); if (typeid(rhsCastExp->getBase()) == typeid(Variable)) { Variable * rhsCastVar = dynamic_cast<Variable*>(&rhsCastExp->getBase()); if (rhsCastVar->var == this->var) { if (typeid(rhsCastExp->getExponent()) == typeid(Integer)) { Integer * integer = dynamic_cast<Integer*>(&rhsCastExp->getExponent()); Number * newExpInt = new Integer(integer->getInt() - 1); Exponent * exponent = new Exponent(*this, *newExpInt); delete integer; delete rhsCastVar; delete rhsCastExp; return *exponent; } } delete rhsCastVar; } delete rhsCastExp; } std::vector<Number*> numbers; std::vector<char> operators; numbers.push_back(this); numbers.push_back(&rhs); operators.push_back('/'); Number * result = new Placeholder(numbers, operators); return *result; }
Expression* Logarithm::simplify(){ if(getArgument()->toDecimal() == 0){ throw "Logarithm: log(0); undefined"; } if(getBase()->toDecimal() == 1){ throw "Logarithm: log_1:x; undefined"; } if((getBase()->toDecimal() <= 0) || (getArgument()->toDecimal() <= 0)){ throw "Logarithm: negative base and/or argument; non-real result"; } if(getArgument()->toDecimal() == 1){ Number* zero = new Number(0); return zero; } if(getArgument()->toDecimal() == getBase()->toDecimal()){ Number* one = new Number(1); return one; } if(getArgument()->getName() == "Exponent"){ vector<Expression*> simpLogVec; Exponent* arg = static_cast<Exponent*>(getArgument()); if(getBase() == arg->getBase()){ return arg->getPower(); } simpLogVec.push_back(arg->getPower()); Logarithm* newLog = new Logarithm(getBase(),arg->getBase()); simpLogVec.push_back(newLog); MultiplicationVector* simpLog = new MultiplicationVector(simpLogVec); return simpLog; } if(log10(getArgument()->toDecimal())/log10(getBase()->toDecimal()) == floor(log10(getArgument()->toDecimal())/log10(getBase()->toDecimal()))){ Number* evalLog = new Number(log10(getArgument()->toDecimal())/log10(getBase()->toDecimal())); return evalLog; } return this; }
Number& Root::operator/(Number& rhs) { if (typeid(rhs) == typeid(Root)) { Root * rhsCast = dynamic_cast<Root*>(&rhs); if (rhsCast->getRoot() == *this->root) { Number * innards = &(this->base->clone() / rhsCast->getBase().clone()); Root * answer = new Root(*innards, this->root->clone()); Number * simplified = &answer->simplify(); delete answer; return *simplified; } else { Exponent * denominator = new Exponent(rhsCast->clone(), rhsCast->getRoot().clone()); Number * numerator = &(rhs.clone() * this->clone()); Number * result = &(numerator->clone() / denominator->simplify()); delete denominator; delete numerator; return *result; } } else { if (typeid(rhs) == typeid(Placeholder)) { Integer * one = new Integer(1); return *one / (rhs.clone() / this->clone()); } else { std::vector<Number*> * numbers = new std::vector<Number*>(); std::vector<char> * operators = new std::vector<char>(); numbers->push_back(&this->clone()); numbers->push_back(&rhs.clone()); operators->push_back('/'); Number * placeholder = new Placeholder(*numbers, *operators); return *placeholder; } } }
// **NOTICE**: In order to avoid circular referencing, this method must be copy and pasted as opposed to // being inherited from the Number class. bool Root::operator==(Number& rhs) { if (typeid(*this) == typeid(rhs)) { if (typeid(rhs) == typeid(Exponent)) { Exponent * rhsCast = dynamic_cast<Exponent*>(&rhs); Exponent * lhsCast = dynamic_cast<Exponent*>(this); if (rhsCast->getBase() == lhsCast->getBase() && rhsCast->getExponent() == lhsCast->getExponent()) { return true; } else { return false; } } else if (typeid(rhs) == typeid(Log)) { Log * rhsCast = dynamic_cast<Log*>(&rhs); Log * lhsCast = dynamic_cast<Log*>(this); if (rhsCast->getBase() == lhsCast->getBase() && rhsCast->getArgument() == lhsCast->getArgument()) { return true; } else { return false; } } else if (typeid(rhs) == typeid(Placeholder)) { Placeholder * rhsCast = dynamic_cast<Placeholder*>(&rhs); Placeholder * lhsCast = dynamic_cast<Placeholder*>(this); if (rhsCast->getNumbers().size() == lhsCast->getNumbers().size()) { for (int i = 0; i < lhsCast->getNumbers().size(); i++) { bool matched = false; for (int y = 0; y < rhsCast->getNumbers().size(); y++) { if (lhsCast[i] == rhsCast[y]) { matched = true; } } if (!matched) { return false; } } for (int i = 0; i < lhsCast->getOperators().size(); i++) { bool matched = false; for (int y = 0; y < rhsCast->getOperators().size(); y++) { if (lhsCast->getOperators()[i] == rhsCast->getOperators()[y]) { if (lhsCast->getOperators()[i] == '-' || lhsCast->getOperators()[i] == '/') { if (lhsCast->getNumbers()[i] == rhsCast->getNumbers()[y] && lhsCast->getNumbers()[i+1] == rhsCast->getNumbers()[y+1]) { matched = true; } else { matched = false; } } else { if (lhsCast->getNumbers()[i] == rhsCast->getNumbers()[y] && lhsCast->getNumbers()[i+1] == rhsCast->getNumbers()[y+1]) { matched = true; } else if (lhsCast->getNumbers()[i+1] == rhsCast->getNumbers()[y] && lhsCast->getNumbers()[i] == rhsCast->getNumbers()[y+1]) { matched = true; } else { matched = false; } } } } if (!matched) { return false; } } return true; } else { return false; } } else if (typeid(rhs) == typeid(Root)) { Root * rhsCast = dynamic_cast<Root*>(&rhs); Root * lhsCast = dynamic_cast<Root*>(this); if (rhsCast->getBase() == lhsCast->getBase() && rhsCast->getRoot() == lhsCast->getRoot()) { return true; } else { return false; } } else if (typeid(rhs) == typeid(Integer)) { Integer * rhsCast = dynamic_cast<Integer*>(&rhs); Integer * lhsCast = dynamic_cast<Integer*>(this); if (rhsCast->getInt() == lhsCast->getInt()) { return true; } else { return false; } } else if (typeid(rhs) == typeid(Variable)) { Variable * rhsCast = dynamic_cast<Variable*>(&rhs); Variable * lhsCast = dynamic_cast<Variable*>(this); if (lhsCast->getVariable() == rhsCast->getVariable()) { return true; } else { return false; } } else { return false; } } else { return false; } }
void ExponentTests::default_constructor_should_set_value_to_zero() { Exponent exponent; CPPUNIT_ASSERT(exponent.toInt() == 0); }
void NobracketString::Multip(string Anumb,string Atype, string Bnumb, string Btype){ isReturnOneNumb = false; if(Atype==Btype){ //if they are the same type; if(Atype == "frac") { Fraction* fra = new Fraction(Anumb); Fraction* frb = new Fraction(Bnumb); fra->Multiplication(*frb); opAnswer = fra->getAnswer(); isReturnOneNumb = true; // here may need to delete the object. } else if(Atype == "int") { Integers* intnumbA = new Integers(Anumb); Integers* intnumbB = new Integers(Bnumb); intnumbA->Multiply(*intnumbB); opAnswer = intnumbA->getAnswer(); //// //delete[] intnumb; isReturnOneNumb = true; } else if(Atype=="log") { Logs* lgA = new Logs(Anumb); Logs* lgB = new Logs(Bnumb); lgA->Multip(*lgB); opAnswer = lgA->getAnswer(); //delete[] lg; if(opAnswer.find("*")<100) //if the opanswer string contains "+", means it return a complex expression isReturnOneNumb = false; else isReturnOneNumb = true; } else if(Atype=="root") { nthRoot* nthNumb = new nthRoot(Anumb); nthRoot* B = new nthRoot(Bnumb); nthNumb->multiply(*B); opAnswer = nthNumb->getAns(); if(opAnswer.find("*")<100) //if the opanswer string contains "+", means it return a complex expression isReturnOneNumb = false; else isReturnOneNumb = true; }//it is handled in the calculating() else if(Atype=="pi"){ // Pi* p = new Pi(Anumb); // p->Multiply(*p); // opAnswer = p->getAnswer(); isReturnOneNumb = true; } else if(Atype=="e"){ Exponential* p = new Exponential(Anumb); p->Multiply(*p); opAnswer = p->getAnswer(); isReturnOneNumb = true; }else if(Atype=="exp"){ Exponent* power = new Exponent(Anumb); Exponent* b = new Exponent(Bnumb); power->multiply(*b); opAnswer = power->getAnswer(); if(opAnswer.find("-")<100) //if the opanswer string contains "+", means it return a complex expression isReturnOneNumb = false; else isReturnOneNumb = true; } } else{ if((Atype=="frac"&&Btype=="int")||(Btype=="frac"&&Atype=="int")){ //if not the same type Fraction* fra = new Fraction(Anumb); Fraction* frb = new Fraction(Bnumb); fra->Multiplication(*frb); opAnswer = fra->getAnswer(); isReturnOneNumb = true; }else if((Atype=="int"&&Btype=="root")||(Btype=="int"&&Atype=="root")){ nthRoot* nthNumb = new nthRoot(Anumb); nthRoot* B = new nthRoot(Bnumb); nthNumb->multiply(*B); opAnswer = nthNumb->getAns(); // if(opAnswer.find("*")<100) //if the opanswer string contains "+", means it return a complex expression // isReturnOneNumb = true; // else isReturnOneNumb = true; } else{ isReturnOneNumb=false; } } }
void NobracketString::divide(string Anumb,string Atype, string Bnumb, string Btype){ //need to handle different types calculation, basicly differen type just return as it is. isReturnOneNumb = false; if(Atype==Btype){ //if they are the same type; if(Atype == "frac") { Fraction* fra = new Fraction(Anumb); Fraction* frb = new Fraction(Bnumb); fra->Division(*frb); opAnswer = fra->getAnswer(); isReturnOneNumb = true; // here may need to delete the object. } else if(Atype == "int") { Integers* intnumbA = new Integers(Anumb); Integers* intnumbB = new Integers(Bnumb); intnumbA->Divide(*intnumbB); opAnswer = intnumbA->getAnswer(); //!!!!!here type has to be a "frac"!!!!! //// //delete[] intnumb; // if(opAnswer.find("/")<100) // isReturnOneNumb = false; // else isReturnOneNumb = true; } else if(Atype=="log") { Logs* lgA = new Logs(Anumb); Logs* lgB = new Logs(Bnumb); lgA->divide(*lgB); opAnswer = lgA->getAnswer(); //delete[] lg; if(opAnswer.find("/")<100){ //if the opanswer string contains "+", means it return a complex expression isReturnOneNumb = false;} else isReturnOneNumb = true; } else if(Atype=="root") { nthRoot* nthNumb = new nthRoot(Anumb); nthRoot* B = new nthRoot(Bnumb); nthNumb->divide(*B); opAnswer = nthNumb->getAns(); if(opAnswer.find("/")<100) //if the opanswer string contains "+", means it return a complex expression isReturnOneNumb = false; else isReturnOneNumb = true; }//it is handled in the calculating() else if(Atype=="pi"){ // Pi* p = new Pi(Anumb); // p->Divide(*p); // opAnswer = p->getAnswer(); isReturnOneNumb = true; } else if(Atype=="e"){ Exponential* p = new Exponential(Anumb); Exponential* b = new Exponential(Bnumb); p->Divide(*b); opAnswer = p->getAnswer(); isReturnOneNumb = true; }else if(Atype=="exp"){ Exponent* power = new Exponent(Anumb); Exponent* b = new Exponent(Bnumb); power->divide(*b); opAnswer = power->getAnswer(); if(opAnswer.find("-")<100) //if the opanswer string contains "+", means it return a complex expression isReturnOneNumb = false; else isReturnOneNumb = true; } }else{ //if not the same type } }
void NobracketString::simplifynumbers(){ //maybe need to delete the object I create here. for(int i = 0; i<somenumbs.size();i++){ string tempnumb = somenumbs[i]; if(tempnumb.find("^")<100 && tempnumb.find("log")>100){ /////this lines needs to go into Exponent* power = new Exponent(somenumbs[i]); somenumbs[i]=power->getAnswer(); if(power->canSimplifyToInt()){ type.push_back("int"); }else if(power->canSimplifyToFrac()){ type.push_back("frac"); }else{ type.push_back("exp"); } } else if(tempnumb.find("rt")<100){ nthRoot* power = new nthRoot(somenumbs[i]); //will do the simplification in constructor. somenumbs[i]=power->getSimp(); //get a string type if(power->canSimplifytoInt()){ type.push_back("int"); } else if(power->canSimpifytoFrac()){ type.push_back("frac"); }else{ type.push_back("root"); } } else if(tempnumb.find("/")<100 && tempnumb.find("p")>100){ //im each value, if it contains /, Fraction* fra = new Fraction(somenumbs[i]); somenumbs[i]=fra->getAnswer(); //change the vector number to the simplify number. tempnumb = fra->getAnswer(); if(fra->canSimplifytoInteger()) { //if it simplifies to int type.push_back("int"); } // put "int" in the vector type; else{ type.push_back("frac"); } } else if(tempnumb.find("log")<100){ Logs* lg = new Logs(somenumbs[i]); somenumbs[i]=lg->getSimplify(); if(somenumbs[i]==expression){ //if user enter a log only and it cannot be simplify // expression = lg->FinalSplit(); //try split it; if(somenumbs[i]==expression){ //if the log cannot be split, do nothing. }else{ somenumbs.erase(somenumbs.begin()); type.clear(); separateString(); simplifynumbers(); } } if(lg->canSimplifytoInt()){ //check if it can be simplified type.push_back("int"); //if it simplifies to int, put "int" to vector type; } else if(lg->canSimplifytoFra()){ type.push_back("frac"); //else if it simplifies to fraction, put "fra" to vector type; }else{ type.push_back("log"); ////cout<<"in the log to log here"<<endl; } } else if(tempnumb.find("Pi")<100||tempnumb.find("pi")<100){ type.push_back("pi"); } else if(tempnumb.find("e")<100){ type.push_back("e"); }else{ type.push_back("int"); } } }
Number& Placeholder::operator+(Number& rhs) { if (typeid(rhs) == typeid(Placeholder)) { Placeholder * rhsCast = dynamic_cast<Placeholder*>(&rhs); std::vector<Number*> rhsNumberList = rhsCast->getNumbers(); std::vector<char> rhsOperatorList = rhsCast->getOperators(); for (int i = 0; i < rhsNumberList.capacity(); i++) { Number * addition = &(*this + *rhsNumberList[i]); if (typeid(addition) == typeid(Placeholder)) { Placeholder * tempPlaceholder = dynamic_cast<Placeholder*>(addition); this->numbers = &tempPlaceholder->getNumbers(); this->operators = &tempPlaceholder->getOperators(); } else { this->numbers->clear(); this->operators->clear(); this->numbers->push_back(addition); } } if (this->numbers->capacity() == 1) { return *this->numbers->at(0); } else { return *this; } } else if (typeid(rhs) == typeid(Exponent)) { Exponent * rhsCast = dynamic_cast<Exponent*>(&rhs); for (int i = 0; i < this->numbers->capacity(); i++) { if (i != 0 && this->operators->at(i-1) == '/') { break; } else if ((i == 0 && this->operators->at(0) == '/') || (i != 0 && this->operators->at(i - 1) == '/')) { Number * toAdd = &(*this->numbers->at(i + 1) * *rhsCast); Number * result = &(*this->numbers->at(i) + *toAdd); return *result; } else if (typeid(this->numbers[i]) == typeid(Exponent)) { Exponent * lhsCast = dynamic_cast<Exponent*>(this->numbers->at(i)); if (this->operators->at(i) == '*' || (i != 0 && this->operators->at(i-1) == '*')) { this->numbers->push_back(&rhs); this->operators->push_back('+'); delete rhsCast; delete lhsCast; return *this; } else if (lhsCast->getBase() == rhsCast->getBase() && lhsCast->getExponent() == rhsCast->getExponent()){ this->numbers->insert(this->numbers->begin() + i - 1, new Integer(2)); this->operators->insert(this->operators->begin() + i - 2, '*'); delete rhsCast; delete lhsCast; return *this; } } else if (i == this->numbers->capacity() - 1) { this->numbers->push_back(&rhs); this->operators->push_back('+'); delete rhsCast; return *this; } } } else if (typeid(rhs) == typeid(Integer)) { Integer * rhsCast = dynamic_cast<Integer*>(&rhs); for (int i = 0; i < this->numbers->capacity(); i++) { if (i != 0 && this->operators->at(i-1) == '/') { break; } else if ((i == 0 && this->operators->at(0) == '/') || (i != 0 && this->operators->at(i - 1) == '/')) { Number * toAdd = &(*this->numbers->at(i + 1) * *rhsCast); Number * result = &(*this->numbers->at(i) + *toAdd); return *result; } else if (typeid(this->numbers[i]) == typeid(Exponent)) { Integer * lhsCast = dynamic_cast<Integer*>(this->numbers->at(i)); this->numbers->assign(i, new Integer(lhsCast->getInt() + rhsCast->getInt())); return *this; } else if (i == this->numbers->capacity() - 1) { this->numbers->push_back(&rhs); this->operators->push_back('+'); delete rhsCast; return *this; } } } else if (typeid(rhs) == typeid(Log)) { Log * rhsCast = dynamic_cast<Log*>(&rhs); for (int i = 0; i < this->numbers->capacity(); i++) { if (i != 0 && this->operators->at(i-1) == '/') { break; } else if ((i == 0 && this->operators->at(0) == '/') || (i != 0 && this->operators->at(i - 1) == '/')) { Number * toAdd = &(*this->numbers->at(i + 1) * *rhsCast); Number * result = &(*this->numbers->at(i) + *toAdd); return *result; } else if (typeid(this->numbers[i]) == typeid(Log)) { Log * lhsCast = dynamic_cast<Log*>(this->numbers->at(i)); if (this->operators->at(i) == '*' || (i != 0 && this->operators->at(i-1) == '*')) { this->numbers->push_back(&rhs); this->operators->push_back('+'); delete rhsCast; delete lhsCast; return *this; } else if (lhsCast->getBase() == rhsCast->getBase() && lhsCast->getArgument() == rhsCast->getArgument()){ this->numbers->insert(this->numbers->begin() + i - 1, new Integer(2)); this->operators->insert(this->operators->begin() + i - 2, '*'); delete rhsCast; delete lhsCast; return *this; } } else if (i == this->numbers->capacity() - 1) { this->numbers->push_back(&rhs); this->operators->push_back('+'); delete rhsCast; return *this; } } } else if (typeid(rhs) == typeid(Root)) { Root * rhsCast = dynamic_cast<Root*>(&rhs); for (int i = 0; i < this->numbers->capacity(); i++) { if (i != 0 && this->operators->at(i-1) == '/') { break; } else if ((i == 0 && this->operators->at(0) == '/') || (i != 0 && this->operators->at(i - 1) == '/')) { Number * toAdd = &(*this->numbers->at(i + 1) * *rhsCast); Number * result = &(*this->numbers->at(i) + *toAdd); return *result; } else if (typeid(this->numbers[i]) == typeid(Root)) { Root * lhsCast = dynamic_cast<Root*>(this->numbers->at(i)); if (this->operators->at(i) == '*' || (i != 0 && this->operators->at(i-1) == '*')) { this->numbers->push_back(&rhs); this->operators->push_back('+'); delete rhsCast; delete lhsCast; return *this; } else if (lhsCast->getBase() == rhsCast->getBase() && lhsCast->getRoot() == rhsCast->getRoot()){ this->numbers->insert(this->numbers->begin() + i - 1, new Integer(2)); this->operators->insert(this->operators->begin() + i - 2, '*'); delete rhsCast; delete lhsCast; return *this; } } else if (i == this->numbers->capacity() - 1) { this->numbers->push_back(&rhs); this->operators->push_back('+'); delete rhsCast; return *this; } } } else if (typeid(rhs) == typeid(Variable)) { Variable * rhsCast = dynamic_cast<Variable*>(&rhs); for (int i = 0; i < this->numbers->capacity(); i++) { if (i != 0 && this->operators->at(i-1) == '/') { break; } else if ((i == 0 && this->operators->at(0) == '/') || (i != 0 && this->operators->at(i - 1) == '/')) { Number * toAdd = &(*this->numbers->at(i + 1) * *rhsCast); Number * result = &(*this->numbers->at(i) + *toAdd); return *result; } else if (typeid(this->numbers[i]) == typeid(Variable)) { Variable * lhsCast = dynamic_cast<Variable*>(this->numbers->at(i)); if (this->operators->at(i) == '*' || (i != 0 && this->operators->at(i-1) == '*')) { this->numbers->push_back(&rhs); this->operators->push_back('+'); delete rhsCast; delete lhsCast; return *this; } else if (lhsCast->getVariable() == rhsCast->getVariable()){ this->numbers->insert(this->numbers->begin() + i - 1, new Integer(2)); this->operators->insert(this->operators->begin() + i - 2, '*'); delete rhsCast; delete lhsCast; return *this; } } else if (i == this->numbers->capacity() - 1) { this->numbers->push_back(&rhs); this->operators->push_back('+'); delete rhsCast; return *this; } } } }