setters function inside constructor c++ - c++

I'm trying to use a setter function inside of a constructor, which I've never done before. It's giving me the following error:
[Error] no match for call to '(Laptop) (const char [5], const char [3], int, int)'
well do i need to write the setter function too ? i mean outside the constructor ? i mean like this
void Laptop::setBrand(char a[])
{
brand=a;}
I think the error is in the second constructor, that takes four arguments, but I'm not able to find it.
Here is the code:
#include <iostream>
#include <stdlib.h>
#include <ctype.h>
#include <string.h>
using namespace std;
class Laptop{
private:
char brand[10];
char processor[10];
int ram;
int hardDrive;
public:
void setBrand(char Bra[]);
void setProcessor(char Pro[]);
void setRam(int Ram);
void setHardDrive(int HDrive);
char *getBrand();
char *getProcessor();
int getRam();
int getHardDrive();
Laptop();
Laptop(char [],char [],int ,int );
};
Laptop::Laptop(){
cout<<"Default constructor called...\n";
strcpy(brand,"None");
strcpy(processor,"None);
ram=0;
hardDrive=0;
}
i think the error is in the constructor
Laptop::Laptop(char Bra[],char Pro[],int Ram,int HDrive)
{
cout<<"Parameterized constructor called...\n";
setBrand(Bra );
setProcessor(Pro );
setRam(Ram);
setHardDrive(HDrive);
}
char *Laptop::getBrand()
{
return brand;
}
char *Laptop::getProcessor()
{
return processor;
}
int Laptop::getRam()
{
return ram;
}
int Laptop::getHardDrive()
{
return hardDrive;
}
int main()
{
Laptop laptopObj1;
Laptop laptopobj1("Dell","i5",4,500);
cout<<"Brand :"<<laptopObj1.getBrand()<<"\n";
cout<<"Processor :"<<laptopObj1.getProcessor()<<"\n";
cout<<"Ram :"<<laptopObj1.getRam()<<"\n";
cout<<"HardDrive :"<<laptopObj1.getHardDrive()<<"\n";
cout<<"Brand :"<<laptopObj2.getBrand()<<"\n";
cout<<"Processor :"<<laptopObj2.getProcessor()<<"\n";
cout<<"Ram :"<<laptopObj2.getRam()<<"\n";
cout<<"HardDrive :"<<laptopObj2.getHardDrive()<<"\n";
}

You have alot of errors here..
Laptop laptopObj1,laptopObj2;
...
laptopObj2("Dell","i5", 4, 500);
You cant use the constructor twice. You used the constructor Laptop() in the first line for both of the object, and then tried to use the second constructor for laptopObj2.
You can change the second line to:
laptopObj2 = Laptop("Dell","i5", 4, 500);
Or even better to define it there:
Laptop laptopObj1;
....
Laptop laptopObj2("Dell","i5", 4, 500);
Another problem is inside your Laptop() constructor definition:
Laptop::Laptop(char Bra[],char Pro[],int Ram,int HDrive)
{
.....
setBrand(Bra []); // Remove the []
setProcessor(Pro []); // Remove the []
....
}
And one more problem: You have no definitions for some functions of the class:
void setBrand(char Bra[]);
void setProcessor(char Pro[]);
void setRam(int Ram);
void setHardDrive(int HDrive);
void display();
EDIT:
One of the objects of c++ is std::string (#include <string>). You can use it instead of char str[]- just simpler way to declare strings in c++. For example, in your case:
/* Replace this: */
char brand[10];
char processor[10];
void setBrand(char Bra[]);
void setProcessor(char Pro[]);
char *getBrand();
char *getProcessor();
/* With this: */
string brand;
string processor;
void setBrand(const string &Bra);
void setProcessor(const string &Pro);
string getBrand();
string getProcessor();

You are passing two const char* as parameter, so you should change this :
Laptop::Laptop(char Bra[],char Pro[],int Ram,int HDrive)
to this:
Laptop::Laptop(const char* ,const char* ,int Ram,int HDrive)

You really should use std::string rather than char[].
On the question of constructors, there is no need to call setters, as the following code demonstrates. C++ has a shortcut for that capability. I have used std::string and fixed all typos.
#include <iostream>
#include <string>
using namespace std;
class Laptop
{
private:
string brand;
string processor;
int ram;
int hardDrive;
public:
void setBrand(string Bra);
void setProcessor(string Pro);
void setRam(int Ram);
void setHardDrive(int HDrive);
string getBrand();
string getProcessor();
int getRam();
int getHardDrive();
Laptop();
Laptop(string, string, int, int);
};
Laptop::Laptop()
: brand("None")
, processor("None")
, ram(0)
, hardDrive(0)
{
cout << "Default constructor called...\n";
}
Laptop::Laptop(string Bra, string Pro, int Ram, int HDrive)
: brand(Bra)
, processor(Pro)
, ram(Ram)
, hardDrive(HDrive)
{
cout << "Parameterized constructor called...\n";
}
string Laptop::getBrand()
{
return brand;
}
string Laptop::getProcessor()
{
return processor;
}
int Laptop::getRam()
{
return ram;
}
int Laptop::getHardDrive()
{
return hardDrive;
}
int main()
{
Laptop laptopObj1;
Laptop laptopObj2("Dell", "i5", 4, 500);
cout << "Brand :" << laptopObj1.getBrand() << "\n";
cout << "Processor :" << laptopObj1.getProcessor() << "\n";
cout << "Ram :" << laptopObj1.getRam() << "\n";
cout << "HardDrive :" << laptopObj1.getHardDrive() << "\n";
cout << "Brand :" << laptopObj2.getBrand() << "\n";
cout << "Processor :" << laptopObj2.getProcessor() << "\n";
cout << "Ram :" << laptopObj2.getRam() << "\n";
cout << "HardDrive :" << laptopObj2.getHardDrive() << "\n";
}
Mike

Related

Class objects not declared in scope

I am currently experiencing a problem that I just can't seem to wrap my head around why it would be occurring.
In my (Unsplit)program I've created a class that defines an entity object and is able to handle its creation and variables just fine (as I've tested before adding
std::string getName(Entity)const;
std::string getType(Entity)const;
int getDamage(Entity)const;
int getHealth(Entity)const;
But when I do... Even though they are already declared publicly in the class and I am fully able to call Initialize(); Attack(); and PrintStats(); just fine, it doesn't see the other four and therefor are not able to be called.
#include <iostream>
#include <string>
#include <math.h>
#include <stdlib.h> /* srand, rand */
#include <time.h> /* time */
using namespace std;
class Entity
{
public:
Entity() { // default constructor
name = "Human";
type = "Normal";
damage = 1;
health = 100;
}
void printStats();
void Initialize(string, string, int, int); //transformer or setting function
void Attack(Entity&); //observer or getter function
std::string getName(Entity)const;
std::string getType(Entity)const;
int getDamage(Entity)const;
int getHealth(Entity)const;
private://data members and special function prototypes
std::string name;
std::string type;
int damage;
int health;
};
void summonEnemy(Entity&);
int main () {
/* initialize random seed: */
srand (time(NULL));
Entity Player;//declaring new class objects
Entity Enemy;//declaring new class objects
Player.Initialize("Player", "Normal", 10, 90);
summonEnemy(Enemy);
return 0;
}
void summonEnemy(Entity &target) {
target.Initialize("Enemy", "Normal", floor(rand() % 20 + 1), floor(rand() % 100));
cout << "An " << getType(target) << " type " << getName(target) << " has appeared with " <<
getHealth(target) << "HP and can do " << getDamage(target) << " damage.";
}
Error message:
error:'getType' Was not defined in this scope.
error:'getName' Was not defined in this scope.
error:'getHealth' Was not defined in this scope.
error:'getDamage' Was not defined in this scope.
Cut off some code to narrow it down such that only what could be the cause of the problem is showing... But honestly its probably something simple that I am not seeing. Any help appreciated.
You are not calling them correctly. They are members of the Entity class, not standalone functions. Remove the Entity parameters from them, as they already have an implicit Entity *this parameter, and then call them like this:
class Entity
{
public:
Entity(); // default constructor
...
std::string getName() const;
std::string getType() const;
int getDamage() const;
int getHealth() const;
...
};
Entity::Entity()
{
Initialize("Human", "Normal", 1, 100);
}
std::string Entity::getName() const
{
return name;
}
std::string Entity::getType() const
{
return type;
}
int getDamage() const
{
return damage;
}
int getHealth() const
{
return health;
}
void summonEnemy(Entity &target)
{
target.Initialize("Enemy", "Normal", floor(rand() % 20 + 1), floor(rand() % 100));
cout << "An " << target.getType() << " type " << target.getName() << " has appeared with " <<
target.getHealth() << "HP and can do " << target.getDamage() << " damage.";
}
getType is a member function of Entity, so you need to call it on an Entity object:
target.getType();
In the class, you could implement it as:
class Entity {
...
std::string getType() const { return type; }
...
};
The same is true for your other three setters.

Object pointer doesn't work

My task was to create an object in class, initialize it and output(using pointer to class). This code compiles perfectly, but the output doesn't appear. I would really appreciate any help, thank you in advance!
#include <iostream>
#include <string>
using namespace std;
class family
{
public:
void setWife(string w)
{w = wife;};
string getWife()
{return wife;};
void setHusband(string h)
{husband = h;};
string getHusband()
{return husband;};
void setSon(string s)
{s = son;};
string getSon()
{return son;};
void setDaughter1(string d1)
{d1 = daughter1;};
string getDaughter1()
{return daughter1;};
void setDaughter2(string d2)
{daughter2 = d2;};
string getDaughter2()
{return daughter2;};
double* getPointer()
{return &pointer;};
void initialize()
{
setWife("Shirley Collin");
setHusband("Donald Collin");
setSon("Collin Collin");
setDaughter1("Harriet Collin");
setDaughter2("Hillary Collin");
}
friend void output(family* Collin);
private:
string wife;
string husband;
string son;
string daughter1;
string daughter2;
double pointer;
};
void output(family* Collin)
{cout << "Husband is " <<Collin->getHusband()<< endl;
cout << "wife is " << Collin ->getWife() << endl;
cout << "son is " << Collin->getSon() << endl;
cout << "daughter1 is " << Collin->getDaughter1() << endl;
cout << "daughter2 is " << Collin->getDaughter2()<< endl;
};
int main()
{family Collin;
Collin.initialize();
family *pointer = new family;
output (pointer);
cin.ignore();
}
family Collin;
Collin.initialize();
This constructs an instance of the family class, and initializes it with the values defined in the initialize() method.
family *pointer = new family;
output (pointer);
This constructs a second instance of the family class, does not initialize it in any way, and calls the output() method, to display the contents of the completely uninitialized second instance of this family class.
This is why this program produces no useful output.
You probably want to replace these four lines with:
family *pointer=new family;
pointer->initialize();
output(pointer);

Error on my first class when trying to display

I'm building a class that will create a vehicle's characteristics and I'm having some difficulties when trying to display autovehicle a1 on the console. I get an error which I cannot explain. Please help, if possible
#include <iostream>
using namespace std;
class Autovehicle {
private:
//registry number
char * car_registration_number;
char engine;
int engine_cc;
int avg_consumption;
int avg_speed;
int avg_consumption_urban;
int avg_speed_urban;
int max_speed;
static int number_of_autovehicles;
public:
//getters
char * get_car_registration_number() {
return this->car_registration_number;
}
char get_engine()
{
return this->engine;
}
int get_engine_cc() {
return this->engine_cc;
}
int get_avg_consumption() {
return this->avg_consumption;
}
int get_avg_speed() {
return this->avg_speed;
}
int get_avg_consumption_urban() {
return this->avg_consumption_urban;
}
int get_avg_speed_urban() {
return this->avg_speed_urban;
}
int get_max_speed() {
return this->max_speed;
}
static int get_number_of_cars() {
return number_of_autovehicles;
}
//setters
void set_car_registration_number(char *car_reg_nr) {
this->car_registration_number = car_reg_nr;
}
void set_engine(char eng) {
this->engine = eng;
}
void set_engine_cc(int eng_cc) {
this->engine_cc = eng_cc;
}
void set_avg_consumption(int avg_cons) {
this->avg_consumption = avg_cons;
}
void set_avg_speed(int avg_spd) {
if (this->avg_speed > avg_spd)
cout << endl << "You should probably slow down";
this->avg_speed = avg_spd;
}
void set_avg_consumption_urban(int avg_cons_urb) {
this->avg_consumption_urban = avg_cons_urb;
}
void set_avg_speed_urban(int avg_spd_urb) {
if (this->avg_speed_urban > avg_spd_urb)
cout << endl << "You should probably slow down";
this->avg_speed_urban = avg_spd_urb;
}
void set_max_speed(int max_spd) {
this->max_speed = max_spd;
}
//default constructor
Autovehicle(){
number_of_autovehicles++;
this->car_registration_number = new char[strlen("There are no autovehicles") + 1];
strcpy(this->car_registration_number, "There are no autovehicles");
this->engine = NULL;
this->engine_cc = 0;
this->avg_consumption = 0;
this->avg_speed = 0;
this->avg_consumption_urban = 0;
this->avg_speed_urban = 0;
this->max_speed = 0;
}
//constructor
Autovehicle(char* car_reg_nr, char eng, int eng_cc, int avg_cons, int avg_spd, int avg_cons_urb, int avg_spd_urb, int max_spd){
number_of_autovehicles++;
this->car_registration_number = new char[strlen(car_reg_nr) + 1];
strcpy(this->car_registration_number, car_reg_nr);
this->engine = eng;
this->engine_cc = eng_cc;
this->avg_consumption = avg_cons;
this->avg_speed = avg_spd;
this->avg_consumption_urban = avg_cons_urb;
this->avg_speed_urban = avg_spd_urb;
this->max_speed = max_spd;
}
//destructor
~Autovehicle() {
delete[]this->car_registration_number;
number_of_autovehicles--;
}
};
This is where the void main, and the problem starts:
void main() {
Autovehicle a1( "Engniasd", "gasoline", 1980, 11, 50, 8, 100) {
cout<<"registration number: "<< this->car_registration_number;
cout << "engine: " << this->engine;
cout << "engine cc:" << this->engine_cc;
cout << "consumption: " << this->avg_consumption;
cout << "avg speed: " << this->avg_speed;
cout << "urban consumption: " << this->avg_consumption_urban;
cout << "urban speed " << this->avg_speed_urban;
}
}
The problem that I'm getting is "No instance of constructor matches the argument list" when trying to display Autovehicle a1(Engniasd, the first term)
Try to add the registration number to your car and the number of vehicles:
Autovehicle a1("REG12345", "gasoline", 1980, 11, 50, 8, 100, 50, 3).
Your constructor defines eng as a char, but you're passing it "gasoline" which is a const char*.
Also, storing the car registration number as a char*. Make your life easier and use a std::string instead. That way you, and your class users, don't need to worry about managing the lifetime of the pointer.
And, in main you've declared a variable called a1 but it looks like you are trying to call methods on it using this. You need to call against the instance variable:
cout << "engine: " << a1.engine;
You also need to terminate the a1 declaration with a semicolon and don't need the braces, eg:
Autovehicle a1( "Engniasd", "gasoline", 1980, 11, 50, 8, 100);
cout << "registration number: "<< a1.car_registration_number;
At school atm and unable to get a good look at this, but look at your constructor, you have a char instead of a char ptr for your 2nd argument. you can't implicitly convert char to const char*, you can char* -> const char*, so change your 2nd argument to a char*. Also, change void main() to int main(), main is supposed to be an int (ansi standard), and many compilers might not accept you using void main().
I see several problems.
Can you explain why car_registration_number and engine have different types?
If you can answer this one for yourself, you can fix one of your issues.
Also you should separate the class declaration from the implementation and make sure that you initialize all the variables. Including the static one.
Problems in calling constructor
Autovehicle(char* , char , int, int, int, int, int, int)
the second parameter is char, but you pass char*, also constructor have 6 int parameters, but you pass only five in main. And you cannot print values of object in your way. Create function in you class
void print()
{
cout<<"registration number: "<< this->car_registration_number;
cout << "engine: " << this->engine;
cout << "engine cc:" << this->engine_cc;
cout << "consumption: " << this->avg_consumption;
cout << "avg speed: " << this->avg_speed;
cout << "urban consumption: " << this->avg_consumption_urban;
cout << "urban speed " << this->avg_speed_urban;
}
and call it in main() as
Autovehicle a1( "Engniasd", "gasoline", 1980, 11, 50, 8, 100, 0);
a1.print();

Object doesn't listen to method or is not created? (C++ OO)

Whenever I try to make an object and call a function on it, it doesn't seem to work.
I have no idea why, since I don't seem to have errors too.
I have searched around on here regarding constructors and the toString-method, but haven't find anything that worked.
I have tried to edit (distinct) the members in the constructor members,
Tried to rewrite the toString method.
Tried to make local object (with no pointer).
But it doesn't return me the things in the object that I created when calling the constructor.
Where does the problem situate in this problem?
Here is my code:
.h file:
#pragma once
#include "stdafx.h"
#include <string>
#include <sstream>
#include <iostream>
using namespace std;
class Store{
private:
int id;
string name;
string adress;
string telephone;
string btwNumber;
public:
int getId();
void setId(int);
string getName();
void setName(string);
string getAdress();
void setAdress(string);
string getTelephone();
void setTelephone(string);
string getBtwNumber();
void setBtwNumber(std::string);
string toString();
Store(int, string, string , string, string);
};
.cpp file:
// Store.cpp : Defines the entry point for the console application.
//
#include "stdafx.h"
#include "Store.h"
Store::Store(int idnum, string nameS, string adreS, string telephonE, string btwnummeR){
idnum = id;
nameS = name;
adreS = adress;
telephonE = telephone;
btwnummeR = btwNumber;
}
int Store::getId()
{
return id;
}
void Store::setId(int id){
this->id = id;
}
string Store::getName(){
return naam;
}
void Store::setName(string name){
this->naam = naam;
}
string Store::getTelephone(){
return telephone;
}
void Store:setTelephone(string telephone){
this->telephone = telephone;
}
string Store::getBtwNumber()
{
return btwNumber;
}
void Store::setBtwNumber(string btwNumber){
btwNumber = btwNumber;
}
string Store::getAdress(){
return adress;
}
void Store::setAdress(string adress){
this->adress = adress;
}
string Store::toString(){
stringstream s;
s << "Id: " << id << endl;
s << "Naam: " << name << endl;
s << "Adres: " << adress << endl;
s << "Telefoonnummer: " << telephone << endl;
s << "BTWnummer: " << btwNumber << endl;
return s.str();
}
int _tmain(int argc, _TCHAR* argv[])
{
Store *test = new Store (4, "Test", "test", "test", "test");
test->toString();
system("Pause");
return 0;
}
Your constructor is inversed: you are assigning member variables to constructor arguments and not vice versa.
nameS = name;
Should be
name = nameS;
And so on
The method toString does work, but it won't magically decide to output its return value to screen. You'll have to do it yourself:
std::cout << test->toString() << std::endl;
You'll need to add #include <iostream> on top of your cpp file.

C++ Pointers In A Game

I am in what seems to be a never ending quest to understand pointers. I finally have a working code using pointers to create a quick character and enemy, then mock an overly simple battle. It works 100% as it seems, but I'm not 100% sure it's correct or what I did to make it right. I have read 13 chapters so far in my C++ book (2 being over pointers specifically), but I'm still not sure it's clicked. If this looks like a valid use and proper utilization of them, I think I'm getting there, just wanted some clarification if it is. Thanks in advance!
#include <iostream>
#include <string>
#ifndef CLASS_H
#define CLASS_H
class Unit
{
public:
Unit(const std::string name, int hp, int power);
~Unit();
void printHP();
void attack(Unit* unit);
bool isDead();
private:
std::string mName;
int mHP;
int mPower;
};
Unit::Unit(const std::string name, int hp, int power)
{
mName = name;
mHP = hp;
mPower = power;
}
void Unit::printHP()
{
std::cout << std::endl;
std::cout << mName << "'s HP: " << mHP << std::endl;
}
void Unit::attack(Unit* unit)
{
std::cout << std::endl;
std::cout << unit->mName << " takes " << this->mPower << " damage! " << std::endl;
unit->mHP -= this->mPower;
}
bool Unit::isDead()
{
return this->mHP < 1;
}
Unit::~Unit()
{
}
#endif
int main()
{
Unit player1("GoodFellow", 20, 5);
Unit Enemy("ABadMan", 10, 2);
while (!Enemy.isDead())
{
player1.printHP();
Enemy.printHP();
player1.attack(&Enemy);
Enemy.attack(&player1);
}
}
Modified it to this... I think I get the reason for only using a reference, just trying to get the concept of pointers....
#include <iostream>
#include <string>
#ifndef CLASS_H
#define CLASS_H
class Unit
{
public:
Unit(const std::string name, int hp, int power);
~Unit();
void printHP();
void attack(Unit& unit);
bool isDead();
void setHP(int hp);
private:
std::string mName;
int mHP;
int mPower;
};
Unit::Unit(const std::string name, int hp, int power)
{
mName = name;
mHP = hp;
mPower = power;
}
void Unit::printHP()
{
std::cout << std::endl;
std::cout << mName << "'s HP: " << mHP << std::endl;
}
void Unit::attack(Unit& unit)
{
std::cout << std::endl;
std::cout << unit.mName << " takes " << this->mPower << " damage! " << std::endl;
unit.mHP -= this->mPower;
}
bool Unit::isDead()
{
return this->mHP < 1;
}
void Unit::setHP(int hp)
{
this->mHP = hp;
}
Unit::~Unit()
{
}
#endif
int main()
{
Unit player1("GoodFellow", 20, 5);
Unit Enemy("ABadMan", 10, 2);
while (true)
{
while (!Enemy.isDead())
{
player1.printHP();
Enemy.printHP();
player1.attack(Enemy);
Enemy.attack(player1);
}
char playAgain;
std::cout << "Fight again? (y)/(n)" << std::endl;
std::cin >> playAgain;
if (playAgain == 'n')
{
break;
}
else
{
Enemy.setHP(10);
}
}
}
Yes, that's a reasonable use of pointers. I was actually glad to see that you used them very little. I was half expecting to see Unit* player1 = new Unit ... and such all over the place. But no, you used automatic storage duration all over (rather than dynamic), which was very appropriate.
So the main reason for passing Unit*s to the attack functions is to that inside the function you can modify the Unit that you're attacking and have the effect seen outside. If you were to pass the Units directly, they would be copied into the function and then the unit->mHP -= this->mPower; would only affect the copy.
However, there is a more appropriate tool at your disposal here. You can use references. A reference also allows you to pass an object without copying it, so that modifications inside the function can be seen outside. Your attack function signature would change to:
void Unit::attack(Unit& unit)
The type Unit& is a "reference to Unit". Don't confuse the use of & with taking the address of an object - it means something completely different here. You would then call it like so:
player1.attack(Enemy);
The point is you should try to avoid pointers as much as possible. Since you can use references here, which are safer (you do not need to check for null), you should use them.
It's fine to learn about how pointers to work, but in doing so, you should learn how to use other more appropriate tools for the job.