dimanche 27 octobre 2019

C++ ComplexFractionText: Ambiguity of overloading, mismatch for operator

I'm getting problems of initializing before int, and also mismatching for operator<< in C++ ComplexFractionText program.

I used Dev-C++ 5.11 and used compiler TDM-GCC 4.9.2 64-bit Release.

The project each uses the following files: Number.h, Fraction.h, Fraction.cpp, ComplexFraction.h, ComplexFraction.cpp, ComplexFractionText.cpp

Error log:

[Error] no match for 'operator>' (operand types are 'std::ofstream {aka std::basic_ofstream<char>}' and 'int')
[Error] no match for 'operator<' (operand types are 'std::ofstream {aka std::basic_ofstream<char>}' and 'int')
[Error] invalid use of 'void'
[Error] no match for 'operator=' (operand types are 'std::ifstream {aka std::basic_ifstream<char>}' and 'int')
[Error] 'menuAction' was not declared in this scope

The expected results I wanted by ComplexFraction program are as the following. (My apologies in preface for long-winded codes a little bit because I'm not sure which to tailor yet.)

[UPDATED] ostream & operator<<(ostream & output, const Fraction & frac1);

ComplexFractions.txt is as following

3 2 5 4
8 9 6 7

Expected OUTPUT:

Current Complex Fraction = 0

-----------------------------

1) Change Complex Fraction

2) Append Complex Fraction to file

3) Print all Complex Fractions in file

4) Quit

1

Real Denominator:2

Real Numerator:3

Imaginary Denominator:4

Imaginary Numerator:5

Current Complex Fraction = (3/2)+(5/4)i

ComplexFraction.cpp

#include <iostream>
#include "Number.h"
#include "Fraction.h"
#include "ComplexFraction.h"

using namespace std;

void ComplexFraction::print() const {
    real.print();
    if(imag.getNumerator() != 0) {
        cout << " + ";
        imag.print();
        cout << "i";
    }
}

void ComplexFraction::setRealAndImaginary(Fraction newReal, Fraction newImag) {
    real = newReal;
    imag = newImag;
}

void ComplexFraction::setReal(Fraction newReal) {
    real = newReal;
}

void ComplexFraction::setImaginary(Fraction newImag) {
    imag = newImag;
}

Fraction ComplexFraction::getReal() const {
    return real;
}

Fraction ComplexFraction::getImaginary() const {
    return imag;
}

ComplexFraction ComplexFraction::operator+(ComplexFraction complex2) {
    ComplexFraction newComplex;
    Fraction newReal = real + complex2.getReal();
    Fraction newImag = imag + complex2.getImaginary();
    newComplex.setRealAndImaginary(newReal, newImag);

    return newComplex;
}

ComplexFraction ComplexFraction::operator-(ComplexFraction complex2) {
    ComplexFraction newComplex;
    Fraction newReal = real - complex2.getReal();
    Fraction newImag = imag - complex2.getImaginary();
    newComplex.setRealAndImaginary(newReal, newImag);

    return newComplex;
}

ComplexFraction ComplexFraction::operator*(ComplexFraction complex2) {
    ComplexFraction newComplex;
    Fraction newReal = real*complex2.getReal() - imag*complex2.getImaginary();
    Fraction newImag = imag*complex2.getReal() + real*complex2.getImaginary();
    newComplex.setRealAndImaginary(newReal, newImag);

    return newComplex;
}

ComplexFraction ComplexFraction::operator/(ComplexFraction complex2) {
    ComplexFraction newComplex;
    Fraction newReal = (real*complex2.getReal() + imag*complex2.getImaginary()) / (complex2.getReal()*complex2.getReal() + complex2.getImaginary()*complex2.getImaginary());
    Fraction newImag = (imag*complex2.getReal() - real*complex2.getImaginary()) / (complex2.getReal()*complex2.getReal() + complex2.getImaginary()*complex2.getImaginary());
    newComplex.setRealAndImaginary(newReal, newImag);

    return newComplex;
}

bool ComplexFraction::operator==(ComplexFraction complex2) {
    return (real == complex2.getReal() && imag == complex2.getImaginary());
}

ostream & operator<<(ostream & output, ComplexFraction & complex1) {
    output << complex1.getReal() << " + j(" << complex1.getImaginary() << ")";
    return output;
}

ComplexFraction.h

using namespace std;

class ComplexFraction : public Number {
    private:
        Fraction real;
        Fraction imag;
    public:
        void print() const;
        void setRealAndImaginary(Fraction newReal, Fraction newImag);
        void setReal(Fraction newReal);
        void setImaginary(Fraction newImag);
        Fraction getReal() const;
        Fraction getImaginary() const;
        ComplexFraction operator+(ComplexFraction complex2);
        ComplexFraction operator-(ComplexFraction complex2);
        ComplexFraction operator*(ComplexFraction complex2);
        ComplexFraction operator/(ComplexFraction complex2);
        bool operator==(ComplexFraction complex2);
};

ostream & operator<<(ostream & output, ComplexFraction & complex1);

ComplexFractionText.cpp

#include <iostream>
#include <fstream>
#include <stdexcept>
#include <string>
#include <cstdlib>

#include "Number.h"
#include "Fraction.h"
#include "ComplexFraction.h"

using namespace std;

int msgReadInt(string message) {
    int inputNum;
    cout << message;
    cin >> inputNum;
    return inputNum;
}

void changeComplexFraction(ComplexFraction & compFrac) {
    Fraction realFrac, imagFrac;
    realFrac.setNumerator(msgReadInt("Real Numerator:")).setDenominator(msgReadInt("Real Denominator:"));
    imagFrac.setNumerator(msgReadInt("Imaginary Numerator:")).setDenominator(msgReadInt("Imaginary Denominator:"));
    compFrac.setReal(realFrac).setImaginary(imagFrac);
}

int chooseFromMenu() {
    int menuNum = 0;
    while (menuNum == 0) {
        try {
            cin >> menuNum;
            if(menuNum < 1 || menuNum > 4) throw runtime_error("Invalid menu item");
        }
        catch (runtime_error & ex) {
            cout << ex.what() << endl;
            menuNum = 0;
        }
    }
    return menuNum;
}

void writeFractionToFile(ComplexFraction compFrac, char * filename) {
    ofstream myfile;
    while (myfile == 0) {
        try {
            cin >> myfile;
            if(myfile < 1 || myfile > 4) throw runtime_error("Invalid menu item");
        }
        catch (runtime_error & ex) {
            cout << ex.what() << endl;
            myfile = 0;
        }
    }
    myfile.open(filename, ios::app);
    // myfile.write
    myfile << compFrac.getReal().getNumerator() << " ";
    myfile << compFrac.getReal().getDenominator() << " ";
    myfile << compFrac.getImaginary().getNumerator() << " ";
    myfile << compFrac.getImaginary().getDenominator() << " ";
    myfile << endl;
    myfile.close();
}

Fraction readFractionFromFile(ifstream & myFile) {
    int numerator, denominator;
    Fraction myFrac;
    // myfile.read
    myFile >> numerator >> denominator;
    myFrac.setNumerator(numerator).setDenominator(denominator);
    return myFrac;
}

void printAllFractions(char * filename) {
    ifstream myfile;
    ComplexFraction compFrac;
    Fraction realFrac, imagFrac;

    myfile.open(filename, ios::in);

    while (myfile == 0) {
        try {
            cin >> myfile;
            if(myfile < 1 || myfile > 4) throw runtime_error("Invalid menu item");
        }
        catch (runtime_error & ex) {
            cout << ex.what() << endl;
            myfile = 0;
        }
    }

    if (!myfile) throw runtime_error("Error opening file");
    while(!myfile.eof()) {
        realFrac = readFractionFromFile(myfile);
        imagFrac = readFractionFromFile(myfile);
        compFrac.setReal(realFrac).setImaginary(imagFrac);
        if (!myfile.eof()) compFrac.print();
        cout << endl;
    }
    myfile.close();
}

void printComplexFraction(ComplexFraction compFrac) {
    cout << endl;
    cout << "Current Complex Fraction = ";
    compFrac.print();
    cout << endl;
    cout << "----------------" << endl;
}

void printMenu() {
    cout << "1) Change Complex Fraction" << endl;
    cout << "2) Append Complex Fraction to file" << endl;
    cout << "3) Print all Complex Fractions in file" << endl;
    cout << "4) Quit" << endl;
}

int main() {
    ComplexFraction cf1;
    int menuChoice;
    char filename[25] = "ComplexFractions.txt";

    while(true) {
        printComplexFraction(cf1);
        printMenu();
        menuChoice = chooseFromMenu();
        menuAction(menuChoice, cf1, filename);
    }
}

Fraction.cpp

#include <iostream>
#include "Number.h"
#include "Fraction.h"

using namespace std;

Fraction::Fraction() {
    setNumerAndDenom(0, 1);
}

Fraction::Fraction(int newNumer) {
    setNumerAndDenom(newNumer, 1);
}

Fraction::Fraction(int newNumer, int newDenom) {
    setNumerAndDenom(newNumer, newDenom);
}

void Fraction::print() const {
    if (denominator == 1) cout << numerator;
    else cout << "(" << numerator << "/" << denominator << ")";
}

void Fraction::setNumerAndDenom(int newNumer, int newDenom) {
    if (newDenom == 0) {
        cout << "Error creating a fraction with a zero denominator" << endl;
        return;
    }
    numerator = newNumer;
    denominator = newDenom;
    simplify();
}

Fraction & Fraction::setNumerator(int newNumer) {
   numerator = newNumer;
   return (*this);
}

Fraction & Fraction::setDenominator(int newDenom) {
    denominator = newDenom;
    return (*this);
}

int Fraction::getNumerator() const {
    return numerator;
}

int Fraction::getDenominator() const {
    return denominator;
}

void Fraction::simplify() {
    int gcd = GreatestCommonDenominator(numerator, denominator);

    numerator /= gcd;
    denominator /= gcd;
}

Fraction Fraction::operator+(Fraction frac2) {
    Fraction newFraction;
    int newDenom = denominator * frac2.getDenominator();
    int newNumer = numerator * frac2.getDenominator() + frac2.getNumerator() * denominator;
    newFraction.setNumerAndDenom(newNumer, newDenom);

    return newFraction;
}

Fraction Fraction::operator-(Fraction frac2) {
    Fraction newFraction;
    int newDenom = denominator * frac2.getDenominator();
    int newNumer = numerator * frac2.getDenominator() - frac2.getNumerator() * denominator;
    newFraction.setNumerAndDenom(newNumer, newDenom);

    return newFraction;
}

Fraction Fraction::operator*(Fraction frac2) {
    Fraction newFraction;
    int newDenom = denominator * frac2.getDenominator();
    int newNumer = numerator * frac2.getNumerator();
    newFraction.setNumerAndDenom(newNumer, newDenom);

    return newFraction;
}

Fraction Fraction::operator/(Fraction frac2) {
    Fraction newFraction;
    int newDenom = denominator * frac2.getNumerator();
    int newNumer = numerator * frac2.getDenominator();
    newFraction.setNumerAndDenom(newNumer, newDenom);

    return newFraction;
}

bool Fraction::operator==(Fraction frac2) {
    return (numerator * frac2.getDenominator() == denominator * frac2.getNumerator());
}

bool Fraction::operator>(Fraction frac2) {
    return (numerator * frac2.getDenominator() > denominator * frac2.getNumerator());
}

bool Fraction::operator<(Fraction frac2) {
    return (numerator * frac2.getDenominator() < denominator * frac2.getNumerator());
}

ostream & operator<<(ostream & output, Fraction & frac) {
    output << frac.getNumerator() << "/" << frac.getDenominator();
    return output;
}

int GreatestCommonDenominator(int num1, int num2) {
    if (num1 == 0) return num2;
    if (num1 < 0) return GreatestCommonDenominator(-num1, num2);
    if (num1 > num2) return GreatestCommonDenominator(num2, num1);
    return GreatestCommonDenominator(num2-num1, num1);
}

Fraction.h

using namespace std;

class Fraction : public Number {
    private:
        int numerator, denominator;
    public:
        Fraction();
        Fraction(int newNumer);
        Fraction(int newNumer, int newDenom);
        void print() const;
        void setNumerAndDenom(int newNumer, int newDenom);
        Fraction & setNumerator(int newNumer);
        Fraction & setDenominator(int newDenom);
        int getNumerator() const;
        int getDenominator() const;
        void simplify();
        Fraction operator+(Fraction frac2);
        Fraction operator-(Fraction frac2);
        Fraction operator*(Fraction frac2);
        Fraction operator/(Fraction frac2);
        bool operator==(Fraction frac2);
        bool operator>(Fraction frac2);
        bool operator<(Fraction frac2);
};

ostream & operator<<(ostream & output, const Fraction & frac1);
int GreatestCommonDenominator(int num1, int num2);

Number.h

class Number {
    public:
        virtual void print() const {};
};

Aucun commentaire:

Enregistrer un commentaire