blob: 1b5ed56a721437ef6d270e65a5c25ad69d62bee3 [file] [log] [blame]
// Written for undergraduate C++ course project at Dept of
// Computer Science, Rutgers University.
#include <iostream>
#include <string.h>
using namespace std;
#include "student3.h"
// evaluation of a constant is the value of the constant.
double const_expr::eval(double numb)
{
return(value);
}
// evaluation of a variable is the input value.
double var_expr::eval(double numb)
{
return(numb);
}
// evaluation of a sum expression is the sum of the values of its
// subexpressions.
double sum_expr::eval(double numb)
{
return(first->eval(numb) + second->eval(numb));
}
// evaluation of a product expression is the product of the values of
// its subexpressions.
double prod_expr::eval(double numb)
{
return(first->eval(numb) * second->eval(numb));
}
// evaluation of a quotient expression of the quotient
// of the values of its subexpressions.
double quotient_expr::eval(double numb)
{
return(first->eval(numb) / second->eval(numb));
}
// An expression is printed recursively such that its left subexpression
// is printed, then the operator, then its right subexpression.
void bin_op_expr::print_me()
{
cout << "(";
first->print_me();
cout << " " << op_name << " ";
second->print_me();
cout << ")";
}
// The derivative of a constant is 0.
expr *const_expr::deriv(strng var)
{
return(new const_expr(0));
}
// The derivative of a variable is 1 if the derivative is in
// respect to the variable, and 0 otherwise.
expr *var_expr::deriv(strng var)
{
if (0/*strcmp(var, name)*/)
return(new const_expr(0));
else
return(new const_expr(1));
}
// The derivative of a sum expression is equal to the sum of the
// derivatives of the subexpressions.
expr *sum_expr::deriv(strng var)
{
expr *dvfirst, *dvsecond;
dvfirst = first->deriv(var);
dvsecond = second->deriv(var);
if ((dvfirst->isconst()) && (dvfirst->eval(0) == 0))
return(dvsecond);
else if ((dvsecond->isconst()) && (dvsecond->eval(0) == 0))
return(dvfirst);
else
return(new sum_expr(dvfirst, dvsecond));
}
// The derivative of a product expression is equal the the sum
// of the products of the first subexpression and the derivative of the
// second subexpression, and the second subexpression and the
// derivative of the first.
expr *prod_expr::deriv(strng var)
{
expr *dvfirst, *dvsecond;
dvfirst = first->deriv(var);
dvsecond = second->deriv(var);
if ((dvfirst->isconst()) && (dvfirst->eval(0) == 0))
{
if ((dvsecond->isconst()) && (dvsecond->eval(0) == 0))
return(dvfirst);
else if ((dvsecond->isconst()) && (dvsecond->eval(0) == 1))
return(first);
else
return(new prod_expr(first, dvsecond));
}
else if ((dvfirst->isconst()) && (dvfirst->eval(0) ==1))
{
if ((dvsecond->isconst()) && (dvsecond->eval(0) == 0))
return(second);
else if ((dvsecond->isconst()) && (dvsecond->eval(0) == 1))
return(new sum_expr(first, second));
else
return(new sum_expr(new prod_expr(first, dvsecond), second));
}
else
{
if ((dvsecond->isconst()) && (dvsecond->eval(0) == 0))
return(new prod_expr(dvfirst, second));
else if ((dvsecond->isconst()) && (dvsecond->eval(0) == 1))
return(new sum_expr(first, new prod_expr(dvfirst, second)));
else
return(new sum_expr(new prod_expr(first, dvsecond),
new prod_expr(dvfirst, second)));
}
}
// The derivative of a quotient expression if equal to:
// (second subexpresssion * derivative of the first) - (the derivative
// of the second * the first subexpression) all over the
// second subexpression squared.
expr *quotient_expr::deriv(strng var)
{
expr *dvfirst, *dvsecond;
dvfirst = first->deriv(var);
dvsecond = second->deriv(var);
if ((dvfirst->isconst()) && (dvfirst->eval(0) == 0))
{
if ((dvsecond->isconst()) && (dvsecond->eval(0) == 0))
return(dvfirst);
else if ((dvsecond->isconst()) && (dvsecond->eval(0) == 1))
if (first->eval(0) == 1)
return(new quotient_expr(new const_expr(-1),
new prod_expr(second, second)));
else
return(new quotient_expr(new prod_expr(new const_expr(-1), first),
new prod_expr(second, second)));
else
if (first->eval(0) == 1)
return(new quotient_expr(new prod_expr(new const_expr(-1), dvsecond),
new prod_expr(second, second)));
else
return(new quotient_expr(new prod_expr(new const_expr(-1),
new prod_expr(dvsecond, first)),
new prod_expr(second, second)));
}
else if ((dvfirst->isconst()) && (dvfirst->eval(0) == 1))
{
if ((dvsecond->isconst()) && (dvsecond->eval(0) == 0))
return(new quotient_expr(dvfirst, second));
else if ((dvsecond->isconst()) && (dvsecond->eval(0) == 1))
return(new quotient_expr(new sum_expr(second,
new prod_expr(new const_expr(-1), first)),
new prod_expr(second, second)));
else
return(new quotient_expr(new sum_expr(second,
new prod_expr(new const_expr(-1),new prod_expr(dvsecond, first))),
new prod_expr(second, second)));
}
else
{
if ((dvsecond->isconst()) && (dvsecond->eval(0) == 0))
return(new quotient_expr(dvfirst, second));
else if ((dvsecond->isconst()) && (dvsecond->eval(0) == 1))
return(new quotient_expr(new sum_expr(new prod_expr(second, dvfirst),
new prod_expr(new const_expr(-1),first)),
new prod_expr(second, second)));
else
return(new quotient_expr(new sum_expr(new prod_expr(second, dvfirst),
new prod_expr(new const_expr(-1), new prod_expr(dvsecond, first))),
new prod_expr(second, second)));
}
}
// LLVM: add main return type.
int main() {
const_expr c(8);
var_expr x("x");
prod_expr simple(new const_expr(123.45), new var_expr("y"));
cout << "c is ";
c.print_me();
cout << "\n and its value at 3 is: " << c.eval(3);
cout << "\n and its derivative with respect to x is: ";
c.deriv("x")->print_me();
cout << "\nx is ";
x.print_me();
cout << "\n and its value at 3 is: " << x.eval(3);
cout << "\n and its derivative with respect to x is: ";
x.deriv("x")->print_me();
cout << "\nsimple is ";
simple.print_me();
cout << "\n and its value at 3 is: " << simple.eval(3);
cout << "\n and its derivative with respect to y is: ";
simple.deriv("y")->print_me();
cout << "\n and its derivative with respect to x is: ";
simple.deriv("x")->print_me();
}