Is there a way to use google test on OOP program? - c++

I'm new to google test and currently I'm writing a test for my OOP program, my OOP program is like this:
#include <iostream>
#include <gtest/gtest.h>
using namespace std;
typedef unsigned int NUM;
class Employee
{
protected:
NUM MaSoThue;
private:
NUM Luong;
NUM CMND;
NUM a;
NUM b;
public:
Employee()
{
MaSoThue = 0;
Luong = 0;
CMND = 0;
}
Employee(NUM mst, NUM luong, NUM cmnd)
{
MaSoThue = mst;
Luong = luong;
CMND = cmnd;
}
//get
int getMaSoThue() const { return MaSoThue; }
int getLuong() const { return Luong; }
int getCMND() const {return CMND;}
//set
void setMaSoThue(NUM mst) {if (MaSoThue==0) MaSoThue = mst;}
void setLuong(NUM luong) {Luong = luong;}
void setCMND(NUM cmnd) {if (CMND==0) CMND = cmnd;}
};
int main()
{
// Objects
Employee PhucTri(111,222,333);
Employee MinhDang;
MinhDang.setMaSoThue(1234);
MinhDang.setLuong(2);
MinhDang.setCMND(8888);
//PhucTri
cout <<"MST cua Phuc Tri: "<< PhucTri.getMaSoThue()<<"\n";
cout << "Luong cua Phuc Tri: " << PhucTri.getLuong() << "\n";
cout << "CMND cua Phuc Tri: " << PhucTri.getCMND() << "\n\n";
//MinhDang
cout << "MST cua Minh Dang: " << MinhDang.getMaSoThue() << "\n";
cout << "Luong cua Minh Dang: " << MinhDang.getLuong() << "\n";
cout << "CMND cua Minh Dang: " << MinhDang.getCMND() << "\n";
}
I created a new file, which is below:
#include <gtest/gtest.h>
#include "FileCode.cc"
int main(){}
TEST(No1, PhucTri){
EXPECT_EQ(PhucTri.getMaSoThue(),111);
}
The compiler says that the object "PhucTri" isn't declared in this scope, but I did create it in my first file, is there any way I can get it right on the object ?

In general, Try to not include .cpp files, declare your class and its methods inside a .h file, define methods in .cpp and then create a test file that includes your header.
You have two options here, either define a test class that has an instance of your class follows instructions here.
Or do something like this :
#include <gtest/gtest.h>
#include "FileCode.h"
TEST(No1, PhucTri)
{
Employee PhucTri(111,222,333);
// initialize your data
// ......
EXPECT_EQ(PhucTri.getMaSoThue(),111);
}

Related

Why copy constructor changed previous object pointer member

#include <iostream>
#include <string.h>
#include "Date.h"
#include "Employee.h"
using std::cout;
using std::endl;
using std::to_string;
class TestOps {
public:
int sex = 1;
string toString() {
return " sex:" + to_string(sex) ;
}
};
class Test {
public:
TestOps* testOps;
Test(const Test& t) :Test{} {
this->testOps = new TestOps{ *(t.testOps) };
};
Test() {
TestOps ops;
//this->testOps = new TestOps{}; // it will be ok with this way
this->testOps = &ops;
}
};
int main() {
// code not understand
Test t1;
cout <<"first testOps:" << t1.testOps->toString() << endl; // sex: 1
Test t2{ t1 };
cout << "first testOps:" << t1.testOps->toString() << endl; // sex: -858893460 ???? why?
cout << "second testOps:" << t2.testOps->toString() << endl; // sex: -858893460 ???? why?
return 0;
}
As you can see, why the first log is as expected while the later logs are not?
Also, t1.testOps address is different from t2.testOps which is as expected.
I have done some research but didn't find the answer. Maybe because I'm pretty new to cpp.

Why are my member functions/class variables outputting the wrong numbers?

I am learning how to use classes in c++. Right now I'm working on a small program which should display the miles per gallon of a vehicle based on the given number of miles and gallons. The assignment says to call member functions within the main function in order to set the member variables within the Auto class. Here is my code:
#include <iostream>
using namespace std;
class Auto {
public:
string model;
int milesDriven;
double gallonsOfGas;
double calculateMilesPerGallon(int milesDriven, double gallonsOfGas) {
return milesDriven / gallonsOfGas;
}
void setModel(string newModel){
model = newModel;
}
void setMilesDriven(int newMiles){
milesDriven = newMiles;
}
void setGallonsOfGas(double newGallons){
gallonsOfGas = newGallons;
}
void output(){
cout << "A " << model << " was driven " << milesDriven << " miles, and used " << gallonsOfGas << endl;
cout << "This car gets " << calculateMilesPerGallon(milesDriven, gallonsOfGas) << "mpg.";
}
};
int main()
{
Auto modelFunction;
Auto milesFunction;
Auto gasFunction;
Auto outputFunction;
string carModel = "Toyota Camry";
int carMiles = 100;
double carGallons = 10;
modelFunction.setModel(carModel);
milesFunction.setMilesDriven(carMiles);
gasFunction.setGallonsOfGas(carGallons);
outputFunction.output();
return 0;
}
It's supposed to display something like "A Toyota Camry was driven 100, and used 10 gallons of gas, and gets 10 mpg." Instead, my output shows "A was driven -1538932792 miles, and used 4.66265e-310
This car gets -infmpg." What am I doing that is causing the output to be like this? I just started using classes so I don't have much experience with them. Thanks for the advice.
The error you're encountering is because you're creating four different Auto objects, each of which will have their own member variables. If you change your main function to the following, it will work:
int main()
{
Auto car;
string carModel = "Toyota Camry";
int carMiles = 100;
double carGallons = 10;
car.setModel(carModel);
car.setMilesDriven(carMiles);
car.setGallonsOfGas(carGallons);
car.output();
return 0;
}
Note that there is now only one 'Auto' object entitled 'car'.
You have to create only one instance of class Auto cause you only want to show the info for one car (with the name "Toyota Camry").
#include <iostream>
using namespace std; // strongly encouraging you to avoid using this
// in file scope
class Auto {
public:
string model;
int milesDriven;
double gallonsOfGas;
double calculateMilesPerGallon(/*no params required*/) {
return milesDriven / gallonsOfGas;
}
void setModel(string newModel){
model = newModel;
}
void setMilesDriven(int newMiles){
milesDriven = newMiles;
}
void setGallonsOfGas(double newGallons){
gallonsOfGas = newGallons;
}
void output(){
cout << "A " << model << " was driven " << milesDriven << " miles, and used " << gallonsOfGas << endl;
cout << "This car gets " << calculateMilesPerGallon() << "mpg.";
}
};
int main()
{
string carModel = "Toyota Camry";
int carMiles = 100;
double carGallons = 10;
Auto car;
car.setModel(carModel);
car.setMilesDriven(carMiles);
car.setGallonsOfGas(carGallons);
car.output();
return 0;
}

C++ Nonstatic member referencing must be relative to specific object

This Complex Number program is supposed to take three arguments from a txt document, the first to indicate whether the subsequent two are numbers in polar or rectangular form, and output every complex number given in both rectangular and polar form. Both the header file and source code are shown here. The txt document is in the following format:
p 50 1.2
r 4 0.8
r 2 3.1
p 46 2.9
p 3 5.6
Without declaring the int inputfile() function as static within the class declarations, the build gives an error 'illegal call of non-static member function'.
With the static declaration of the function (shown below), the build gives errors referring to the class members Pfirst, Psecond, Rfirst and Rsecond inside function definition inputfile(), being 'illegal references to non-static members'.
The member declarations cannot then be made static as well because the class would not be able to initialise the parameters within the constructor.
How can I bypass this 'static' problem?
#define Complex_h
class Complex
{
char indicator;
const double pi;
public:
double Pfirst, Psecond, Rfirst, Rsecond;
Complex(char i = 0, double Pf = 0, double Ps = 0, double Rf = 0, double Rs = 0, const double pi = 3.14159265) // with default arguments (= 0)
: indicator(i), Pfirst(Pf), Psecond(Ps), Rfirst(Rf), Rsecond(Rs), pi(pi) {}
~Complex();
void poltorect();
void recttopol();
static int inputfile();
};
#include <iostream>
#include <iomanip>
#include <fstream>
#include <sstream>
#include <string>
#include "Complex.h"
using namespace std;
int Complex::inputfile()
{
ifstream ComplexFile;
ComplexFile.open("PolarAndRectangular.txt");
string TextArray[3];
string TextLine;
stringstream streamline, streamfirst, streamsecond;
while (getline(ComplexFile,TextLine))
{
streamline << TextLine;
for (int j=0; j<3; j++)
{streamline >> TextArray[j];}
streamline.str("");
streamline.clear();
if (TextArray[0] == "r")
{
streamfirst << TextArray[1];
streamfirst >> Rfirst;
streamsecond << TextArray[2];
streamsecond >> Rsecond;
cout << "Complex number in rectangular form is " << Rfirst << "," << Rsecond << endl;
void recttopol();
cout << "Complex number in polar form is " << Pfirst << "," << Psecond << endl;
}
else
{
streamfirst << TextArray[1];
streamfirst >> Pfirst;
streamsecond << TextArray[2];
streamsecond >> Psecond;
cout << "Complex number in polar form is " << Pfirst << "," << Psecond << endl;
void poltorect();
cout << "Complex number in rectangular form is" << Rfirst << "," << Rsecond << endl;
}
streamfirst.str("");
streamfirst.clear();
streamsecond.str("");
streamsecond.clear();
}
ComplexFile.close();
system("pause");
return 0;
}
void Complex::recttopol()
{
Pfirst = sqrt((Rfirst*Rfirst)+(Rsecond*Rsecond));
Psecond = (atan(Rsecond/Rfirst))*(pi/180);
}
void Complex::poltorect()
{
Rfirst = Pfirst*(cos(Psecond));
Rsecond = Pfirst*(sin(Psecond));
}
int main()
{
Complex::inputfile();
system("pause");
return 0;
}
You forgot to create an object of type Complex.
Make your inputfile() method nonstatic and do:
int main()
{
Complex complex; // Object construction.
complex.inputfile();
system("pause");
return 0;
}

Concept of data storing in c++

I have a Spieler class and a Verein class with a vector of Spieler members.
Now if I change something of the Players like the Staerke(german for strength) by using a function of this class in the player class it does not automatically change the value for this player.
Here is the code:
#include <vector>
#include<iostream>
#include <string>
using namespace std;
class Spieler
{
public:
void setinformation(int a, string b, string c, int d)
{
ID = a;
Vorname = b;
Nachname = c;
Staerke = d;
}
void getinformation()
{
cout << "ID: " << ID << endl;
cout << "Vorname: " << Vorname << endl;
cout << "Nachname: " << Nachname << endl;
cout << "Staerke: " << Staerke << endl << endl;
}
void setStaerke(int x)
{
Staerke = x;
}
int getStaerke()
{
return Staerke;
}
private:
string Vorname, Nachname;
int Staerke, ID;
};
class Verein
{
public:
void setSpielerListe(vector<Spieler> x)
{
Spielerliste = x;
}
vector<Spieler> getSpielerListe()
{
return Spielerliste;
}
string getVereinsName()
{
return VereinsName;
}
int getVereinsID() const
{
return VereinsID;
}
void setVereinsID(int x)
{
VereinsID = x;
}
int getGesamtstaerke()
{
Gesamtstaerke = 0;
vector<Spieler> b;
b = getSpielerListe();
for (size_t i = 0; i < b.size(); i++)
{
Gesamtstaerke = Gesamtstaerke + b[i].getStaerke();
}
return Gesamtstaerke;
}
void Vereinsinformationen()
{
vector<Spieler> list;
int id;
string vereinsname;
int gesamtstaerke;
id = getVereinsID();
vereinsname = getVereinsName();
gesamtstaerke = getGesamtstaerke();
list = getSpielerListe();
cout << "VereinsID: " << id << endl;
cout << "Vereinsname: " << vereinsname << endl;
cout << "Gesamstaerke: " << gesamtstaerke << endl << endl;
cout << "Spieler: " << endl;
for (size_t i = 0; i < list.size(); i++)
list[i].getinformation();
}
private:
vector<Spieler> Spielerliste;
int VereinsID, Gesamtstaerke;
string VereinsName;
};
vector<Spieler> spieler;
int main()
{
Spieler Spieler1;
Spieler1.setinformation(0, "Peter", "Pan", 10);
spieler.emplace_back(Spieler1);
Verein Team1;
Team1.setSpielerListe(spieler);
Spieler1.setStaerke(20);
Team1.Vereinsinformationen();
cin.get();
return 0;
}
I'm really new into c++ and programming so the code might be terrible.
Guess it has to do with pointers, I'm really not into the concept of storing data in c++, try to get it by trial & error; So how to change the Staerke in a way that it is changed in the Teams Playerlist too?
The problem is you are storing full object in the vector and not pointers. When you run this line:
spieler.emplace_back(Spieler1);
a copy of Spieler1 is made and put in the vector. So modifying it in the main will have no effect in the vector. Also not that you are copying the vector when setting in Verein class.
You should use pointer if this is what you are after or better yet have a function to modify strength from Verein class taking its id and new strength as parameters might be a good idea. Something like this:
void setStaerke(int id, int x)
{
vector<Spieler>::iterator it = Spielerliste.begin();
while (it != Spielerliste.end())
{
if ((*it).GetId() == id)
{
(*it).setStaerke(x);
break;
}
}
}
If you have access to C++11, it could be made more elegantly.
Hereby you pass and store a copy from the vector into the object:
Team1.setSpielerListe(spieler);
Therefore changes to the original vector and the contained objects will not affect the member.
Further, I don't have much experience with emplace_back, but the more usual way to append an object to a std::vector would also append a copy:
spieler.push_back(Spieler1);
Therefore changes to the original object would not affect the object you've appended to the container.
Make sure you better understand when objects are copied.
For reference:
http://en.cppreference.com/w/cpp/container/vector/emplace_back
http://en.cppreference.com/w/cpp/container/vector/push_back
How to pass objects to functions in C++?

c++ Passing a value the wrong way?

When i am passing an object to a function, I am getting undesired results. It seems to happen when I pass a Character through a Mage's action() function.
Here are some snippits of my code:
character.h
class Character {
public:
Character();
int getMaxLives() const;
int getMaxCraft() const;
protected:
maxLives;
maxCraft;
};
character.cpp
#include "character.h"
Character::Character () {
maxLives = 5;
MaxCraft = 10;
}
int Character::getMaxLives() const {
return maxLives;
}
int Character::getMaxCraft() const {
return maxCraft;
}
mage.h
#include "character.h"
class Mage {
public:
Mage();
void action(Character c1);
};
mage.cpp
#include "mage.h"
Mage::Mage () { ... }
void Mage::action(Character c1) {
cout << "Max Craft: " << c1.getMaxCraft() << endl;
cout << "Max Lives: " << c1.getMaxLives() << endl;
}
driver.cpp
int main () {
Character c1;
Mage m1;
m1.action(c1);
My ouput gives me the following:
Max Craft: 728798402 (The number varies)
Max Lives: 5
However, if in my diver, i do:
cout << "Max Craft: " << c1.getMaxCraft() << endl;
cout << "Max Lives: " << c1.getMaxLives() << endl;
I get:
Max Craft: 10
Max Lives: 5
Any ideas?
Looks like you meant for MaxCraft = 10; (in your default constructor) to actually be maxCraft = 10;. As #chris says in the comments, it appears that you're using some (evil, evil) C++ extension that allows implicitly-typed variables, so the MaxCraft = 10; line is simply defining a new variable named MaxCraft.