1

In this project, I am expected to created a Polynomial class. Here's is what I have for the Polynomial.cpp file:

#include <iostream>
#include "Polynomial.h"
#include <stdexcept>
#include <iomanip>
#include <cmath>
#include <string>

using namespace std;

Polynomial::Polynomial(double c[], int size){ 
    set(c,size);
}

Polynomial::Polynomial(const Polynomial &poly){
    size = poly.size;
    c = new double[size];
    for(int i=0; i<size; i++){
        c[i] = poly.c[i];
    }
}

Polynomial::~Polynomial(){
    delete [] c;
}

void Polynomial::set(double ca[], int s){
    if(s < 1){
        throw std::invalid_argument("Size must be larger or equal to 1.");
    }
    else{
        size = s;
        c = new double[size];
        for(int i=0; i<size; i++){
            c[i] = ca[i];
        }
    }
}

double* Polynomial::getPointer() const{
    return c;
}

int Polynomial::getSize() const{
    return size;
}

bool Polynomial::operator ==(const Polynomial& poly) const{
    if(size != poly.size){
        return false;
    }
    int i = 0;
    int count = 0;
    while ( i < size ) {
        if ( c[i] == poly.c[i] ) {
            count++;
        }
        i++;
    }
    if ( count != size) {
        return false;
    }
    return true;
}

Polynomial Polynomial::operator +(const Polynomial& poly) const{
    int d = fabs(size - poly.size); //absolute value of size difference
    int bigger = size; //the size of the bigger polynomial
    int smaller = poly.size; //the size of the smaller polynomial
    if ( poly.size > size) {
        bigger = poly.size;
        smaller = size;
    }
    double r[bigger];
    double s[bigger];  //new coef array for the smaller polynomial with zeros coefs added

    if ( d != 0 ) {
        if(smaller = poly.size){
            for(int i=0; i < smaller; i++){
                s[i] = poly.c[i];
            }
            for(int i=smaller; i < bigger; i++){
                s[i] = 0;
            }
            for(int i=0; i < bigger; i++){
                r[i] = c[i] + s[i];
            }
        }
        else{
            for(int i=0; i < smaller; i++){
                s[i] = c[i];
            }
            for(int i=smaller; i < bigger; i++){
                s[i] = 0;
            }
            for(int i=0; i < bigger; i++){
                r[i] = poly.c[i] + s[i];
            }
        }
    }
    else {
        for ( int i = 0; i < bigger; i++) {
            r[i] = c[i] + poly.c[i];
        }
    }

    return Polynomial(r,bigger);
}

ostream& operator<<(ostream &lhs, const Polynomial &poly){
    string plus = "+";
    bool valid = false; //check if the first term of the polynomial to be printed is valid or not, valid is true when term is non-zero

if(poly.getPointer()[poly.getSize()-1] < 0){
    if(poly.getPointer()[poly.getSize()-1] != 0){
        lhs << setprecision(1) << fixed << poly.getPointer()[poly.getSize()-1] << "x^" << poly.getSize()-1 << " ";
    }
    for(int i=poly.getSize()-2; i >= 0; i--){
        if(poly.getPointer()[i] != 0 && i != 1 && i != 0){
            if(poly.getPointer()[i] > 0){
                lhs << setprecision(1) << fixed << plus << poly.getPointer()[i] << "x^" << i << " ";
            }
            else{
                lhs << setprecision(1) << fixed << poly.getPointer()[i] << "x^" << i << " ";
            }
        }
        else if(poly.getPointer()[i] != 0 && i == 1){
            if(poly.getPointer()[i] > 0){
                lhs << setprecision(1) << fixed << plus << poly.getPointer()[i] << "x" << " ";
            }
            else{
                lhs << setprecision(1) << fixed << poly.getPointer()[i] << "x" << " ";
            }
        }
        else if(poly.getPointer()[i] != 0 && i == 0){
            if(poly.getPointer()[i] > 0){
                lhs << setprecision(1) << fixed << plus << poly.getPointer()[i];
            }
            else{
                lhs << setprecision(1) << fixed << poly.getPointer()[i];
            }
        }
    }
}
else{
    if(poly.getPointer()[poly.getSize()-1] != 0){
        lhs << setprecision(1) << fixed << noshowpos << poly.getPointer()[poly.getSize()-1] << "x^" << poly.getSize()-1 << " ";
        valid = true;
    }
    for(int i=poly.getSize()-2; i >= 0; i--){
        if(poly.getPointer()[i] != 0 && i != 1 && i != 0){
            if(poly.getPointer()[i] > 0 && valid == true){
                lhs << setprecision(1) << fixed << plus << poly.getPointer()[i] << "x^" << i << " ";
            }
            else{
                lhs << setprecision(1) << fixed << poly.getPointer()[i] << "x^" << i << " ";
                valid = true;
            }
        }
        else if(poly.getPointer()[i] != 0 && i == 1){
            if(poly.getPointer()[i] > 0 && valid == true){
                lhs << setprecision(1) << fixed << plus << poly.getPointer()[i] << "x" << " ";
            }
            else{
                lhs << setprecision(1) << fixed << poly.getPointer()[i] << "x" << " ";
                valid = true;
            }
        }
        else if(poly.getPointer()[i] != 0 && i == 0){
            if(poly.getPointer()[i] > 0 && valid == true){
                lhs << setprecision(1) << fixed << plus << poly.getPointer()[i];
            }
            else{
                lhs << setprecision(1) << fixed << poly.getPointer()[i];
                valid = true;
            }
        }
    }
}
return lhs;

}

Here is my test program:

#include <iostream>
#include "Polynomial.h"
#include <iomanip>

using namespace std;

int main() {
double c[] = {0,-5,3};
double d[] = {3,0,-5,0};

Polynomial p1(c,3);
Polynomial p2(d,4);
cout << "Polynomial p1 is: " << p1 << endl;
cout << "Degree of polynomial p1 is: " << noshowpos << p1.getDegree() << endl;
cout << "Polynomial p2 is: " << p2 << endl;

Polynomial p3(p1);
cout << "Polynomial p3 now is equal to p1 after copy constructor: " << p3 << endl;

bool same = p1 == p3;
cout << "Is p1 equal to p3? " << noshowpos << same << endl;

Polynomial p4 = p1 + p2;
cout << "Polynomial p4 is the sum of p1 and p2: " << p4 << endl;

So the problem I am having is with this if statement:

if(poly.getPointer()[poly.getSize()-1] != 0){
    lhs << setprecision(1) << fixed << poly.getPointer()[poly.getSize()-1] << "x^" << poly.getSize()-1 << " ";
}

When I perform the operator+ for p4 = p1 + p2, the Polynomial array of double for p4 is [3, -5, -2, 0]. So the last value of p4[size - 1] of this array is 0. As you can see above in the if statement, when I get the poly.getPointer()[poly.getSize()-1] value, it equals to 0; however when I compare it with the zero in the if statement, it still executes even though the if statement is false (0 is not equal to 0 so it should skip this if statement). I have tried running it both on an IDE and on a Linux engine; however, the result is still the same. I am not sure if it is related to this constructor which calls the set method:

Polynomial::Polynomial(double c[], int size){ 
    set(c,size);
}

void Polynomial::set(double ca[], int s){
    if(s < 1){
        throw std::invalid_argument("Size must be larger or equal to 1.");
    }
    else{
        size = s;
        c = new double[size];
        for(int i=0; i<size; i++){
            c[i] = ca[i];
        }
    }
}

Please help. Thank you.

Allen
  • 35
  • 6
  • 4
    You can't really compare floating point values for exact equality on computers. See e.g. [Is floating point math broken?](https://stackoverflow.com/questions/588004/is-floating-point-math-broken) for some details – Some programmer dude Nov 17 '18 at 05:15
  • [What is the most effective way for float and double comparison?](https://stackoverflow.com/q/17333/995714), [How dangerous is it to compare floating point values?](https://stackoverflow.com/q/10334688/995714), [c++ comparison of two double values not working properly](https://stackoverflow.com/q/18971533/995714), [Why doesn't my floating-point comparison work?](http://www.cs.technion.ac.il/users/yechiel/c++-faq/floating-point-arith.html) https://floating-point-gui.de/ – phuclv Nov 17 '18 at 06:22
  • @Someprogrammerdude If you can't compare values, you can do computations either. – curiousguy Nov 17 '18 at 14:18
  • @curiousguy Comparisons for ***exact equality*** I said. Comparisons in general (like larger/less than, or equality with an epsilon) are just fine. And on the subject of computations, the more of them you do with floating point values, the more inexact they become. – Some programmer dude Nov 17 '18 at 14:33
  • @Someprogrammerdude If you can't compare for equality, the compiler is broken. So you can't compare at all. – curiousguy Nov 17 '18 at 14:35
  • @curiousguy Okay, I'm not saying that it's not allowed to compare using `==` with floating point values, or that the compiler wont' allow it or something like that. I'm saying that it's pointless since floating point values tend to lose precision after a few calculations due to rounding errors, and what you might think is `12.345` might not be *exactly* `12.345`. That makes comparisons using `==` *pointless* since it seldom will *seem* to work the way beginners believe. – Some programmer dude Nov 17 '18 at 14:39
  • @Someprogrammerdude Comparing for equality *should* do what it usually does, that is check that one value is a copy of another, or two values were obtained by the same computations based on the same values, or two values used in the same "normal" computation will give the same result. – curiousguy Nov 17 '18 at 14:43

0 Answers0