C++ proper usage of ostream inside a class and passing arguments? - c++

I've recently started learning c++ and for the life of me, I can't seem to get the syntax of using ostream in a class and what arguments should I pass. Here's the code:
This is the class in question:
#include <iostream>
#include <string>
using namespace std;
class Pokemon{
friend ostream& operator<<(ostream&, Pokemon);
public:
string name, level, cp;
Pokemon(string x="Pikachu", string y="5", string z="1000"){
name = x;
level = y;
cp = z;
}
Pokemon name(){
return this->name;
}
Pokemon level(){
return this->level;
}
Pokemon cp(){
return this->cp;
}
Pokemon display_stats(){
cout << this-> name << "stats are:" << endl;
cout << " " << "Attack: 2716.05" << endl;
cout << " " << "Defence: 1629.63" << endl;
cout << " " << "HP: 1086.42" << endl;
}
};
template<typename TYPE> //i dont understand this and the things i've written down here are only based on samples i've seen
ostream& operator<<(ostream& os, Pokemon & c){
os << "The level of " << c.name << " is" << c.level << " with cp of " << c.cp;
}
As you could see, I already tried constructing the ostream thing but I don't really understand how it works. This is my main function:
int main()
{
Pokemon a, b, c, d;
a = Pokemon();
b = Pokemon("Weezing");
c = Pokemon("Nidoking", 100);
d = Pokemon("Mewtwo", 50, 5432.1);
cout << a << endl;
cout << b << endl;
cout << c << endl;
cout << d << endl;
cout << "Jessie: You are no match to me! Go " << b.name << "!" << endl;
cout << "Gary: Go lvl " << c.level << " " << c.name << "! Crush them" << endl;
cout << "Ash: " << a.name << " can do it even thouh he is only level " << a.level << endl;
cout << "Jessie: Hahaha! My " << b.name << " CP is " << b.cp << endl;
cout << "Gary: "<< c.name << " CP is " << c.cp << endl;
cout << "Ash: " << a.name << " CP is " << a.cp << endl;
cout << "Giovanni: Behold " << d.name << " is here." << endl;
d.display_stats();
return 0;
}
I'm getting errors of:
no instance of constructor "Pokemon::Pokemon" matches the argument list -- argument types are: (const char [9], int) //on line c = Pokemon("Nidoking", 100);
no instance of constructor "Pokemon::Pokemon" matches the argument list -- argument types are: (const char [7], int, double) //on line d = Pokemon("Mewtwo", 50, 5432.1);

All of your Pokemon class methods are returning the wrong type. And your main() is not calling any of the methods correctly at all.
Change your Pokemon class to look more like this:
#include <iostream>
#include <string>
using namespace std;
class Pokemon {
private:
string m_name;
int m_level;
double m_cp;
friend ostream& operator<<(ostream&, const Pokemon&);
public:
Pokemon(string x="Pikachu", int y=5, double z=1000) {
m_name = x;
m_level = y;
m_cp = z;
}
string name() const {
return m_name;
}
int level() const {
return m_level;
}
double cp() const {
return m_cp;
}
void display_stats() const {
cout << m_name << " stats are:" << endl;
cout << " " << "Attack: 2716.05" << endl;
cout << " " << "Defense: 1629.63" << endl;
cout << " " << "HP: 1086.42" << endl;
}
};
ostream& operator<<(ostream& os, const Pokemon &c) {
os << "The level of " << c.m_name << " is " << c.m_level << " with cp of " << c.m_cp;
return os;
}
And then change main() to look more like this:
int main()
{
Pokemon a;
Pokemon b("Weezing");
Pokemon c("Nidoking", 100);
Pokemon d("Mewtwo", 50, 5432.1);
cout << a << endl;
cout << b << endl;
cout << c << endl;
cout << d << endl;
cout << "Jessie: You are no match to me! Go " << b.name() << "!" << endl;
cout << "Gary: Go lvl " << c.level() << " " << c.name() << "! Crush them" << endl;
cout << "Ash: " << a.name() << " can do it even though he is only level " << a.level() << endl;
cout << "Jessie: Hahaha! My " << b.name() << " CP is " << b.cp() << endl;
cout << "Gary: " << c.name() << " CP is " << c.cp() << endl;
cout << "Ash: " << a.name() << " CP is " << a.cp() << endl;
cout << "Giovanni: Behold " << d.name() << " is here." << endl;
d.display_stats();
return 0;
}
Live Demo

Related

Compiler error - is private within this context - Line 31

#include<iostream>
#include<string>
using namespace std;
class Item{
private:
string type;
string abbrv;
string uID;
int aircraft;
double weight;
string destination;
public:
void print(){
cout << "ULD: " << type << endl;
cout << "Abbreviation: " << abbrv << endl;
cout << "ULD-ID: " << uID << endl;
cout << "Aircraft: " << aircraft << endl;
cout << "Weight: " << weight << " Kilograms" << endl;
cout << "Destination: " << destination << endl;
}
friend void kilotopound(Item);
};
void kilotopound(Item I){
cout << "Weight in Pounds: " << I.weight * 2.2 << " LBS " << endl;
}
int main(){
Item I;
I.type = "Container";
I.uID = "AYK68943IB";
I.abbrv = "AYK";
I.aircraft = 737;
I.weight = 1654;
I.destination = "PDX";
I.print();
kilotopound(I);
return 0;
}
Starting on line 31 I'm getting the error 'std::__cxxll::string Item::type' is private within this context
I'm basically trying to make the data private from this code
class Item{
public:
string type;
string abbrv;
string uID;
int aircraft;
double weight;
string destination;
void print(){
cout << "ULD: " << type << endl;
cout << "Abbreviation: " << abbrv << endl;
cout << "ULD-ID: " << uID << endl;
cout << "Aircraft: " << aircraft << endl;
cout << "Weight: " << weight << " Kilograms" << endl;
cout << "Destination: " << destination << endl;
}
friend void kilotopound(Item);
};
void kilotopound(Item I){
cout << "Weight in Pounds: " << I.weight * 2.2 << " LBS " << endl;
}
int main(){
Item I;
I.type = "Container";
I.uID = "AYK68943IB";
I.abbrv = "AYK";
I.aircraft = 737;
I.weight = 1654;
I.destination = "PDX";
I.print();
kilotopound(I);
return 0;
}
Any help would be greatly appreciated, I'm just sort of lost on how I can resolve the error. Thanks!
Also I need to be able to copy and output the copied data once again if anyone can help with that as well, with private data too. Thanks again!
#include<iostream>
#include<string>
using namespace std;
class Item{
private:
string type;
string abbrv;
string uID;
int aircraft;
double weight;
string destination;
public:
Item(string t, string a, string u, int aC, double w, string d){
type = t;
abbrv = a;
uID = u;
aircraft = aC;
weight = w;
destination = d;
}
void print() {
cout << "ULD: " << type << endl;
cout << "Abbreviation: " << abbrv << endl;
cout << "ULD-ID: " << uID << endl;
cout << "Aircraft: " << aircraft << endl;
cout << "Weight: " << weight << " Kilograms" << endl;
cout << "Destination: " << destination << endl;
}
friend void kilotopound(Item);
};
void kilotopound(Item I){
cout << "Weight in Pounds: " << I.weight * 2.2 << " LBS " << endl;
}
int main(){
Item I ("Container", "AYK68943IB", "AYK", 737, 1654, "PDX");
I.print();
kilotopound(I);
return 0;
}

Questions about right value reference in C++

#include <iostream>
using namespace std;
void swap(int& a, int& b)
{
cout << "address of a: " << &a << " value of a: " << a << endl;
cout << "address of b: " << &b << " value of b: " << b << endl;
int tmp{move(a)};
cout << "address of tmp: " << &tmp << " value of tmp: " << tmp << endl;
a = move(b);
b = move(tmp);
cout << "address of a: " << &a << " value of a: " << a << endl;
cout << "address of b: " << &b << " value of b: " << b << endl;
}
void swap_no_move(int& a, int& b)
{
cout << "address of a: " << &a << " value of a: " << a << endl;
cout << "address of b: " << &b << " value of b: " << b << endl;
int tmp{ a };
cout << "address of tmp: " << &tmp << " value of tmp: " << tmp << endl;
a = b;
b = tmp;
cout << "address of a: " << &a << " value of a: " << a << endl;
cout << "address of b: " << &b << " value of b: " << b << endl;
}
int main() {
int a = 10;
int b = 5;
swap(a, b);
cout << endl;
int c = 10;
int d = 5;
swap_no_move(c, d);
cin.get();
return 0;
}
I have two swap functions: swap and swap_no_move. According to what I read from the book, there should be no "copy" in function swap which means the address of tmp should be the same for tmp and an in function swap. However, the output I got shows there is no difference between these two functions, did I do something wrong?
The definition
int tmp{move(a)};
doesn't move the reference or the variable a itself. It creates a brand new variable tmp which the compiler allocates space for. Then the value of a is moved into tmp.
And since moving int values can't really be done, it's exactly the same as
int tmp = a;

C++ "Class Enum" Novice Problems

I'm starting learning to code in C++ (coming from VB.net) and i need some help in enum class usage.
I've done this simple code from a lerning exercise (originally divided in header.h and Exercise.cpp, but i putted it all together here):
#include <iostream>
#include <string>
#define BEGIN_WITH(x) { \
auto &_ = x;
#define END_WITH() }
using namespace std;
enum class Gender { Male, Female };
struct PersonStruct {
string _Name;
string _SurName;
int _Age;
double _Heigth;
Gender _Gender; };
class Person { public:
string _Name{};
string _SurName{};
int _Age{};
double _Heigth{};
Gender _Gender{}; };
int ModifyPerson(Person& PassPersona, PersonStruct Attribute) {
PassPersona._Name = Attribute._Name;
PassPersona._SurName = Attribute._SurName;
PassPersona._Heigth = Attribute._Heigth;
PassPersona._Age = Attribute._Age;
PassPersona._Gender = Attribute._Gender;
return(0); }
int main() { Person TestingPerson;
BEGIN_WITH(TestingPerson)
_._Age = 23;
_._Gender = Gender::Male;
_._Heigth = 1.94;
_._Name = "John";
_._SurName = "Smith";
END_WITH()
cout << "Person attributes: " << endl;
cout << "Name: " << TestingPerson._Name << endl;
cout << "Surname: " << TestingPerson._SurName << endl;
cout << "Age: " << TestingPerson._Age << endl;
cout << "Gender: " << TestingPerson._Gender << endl;
cout << "Heigth: " << TestingPerson._Heigth << endl;
cout << endl;
ModifyPerson(TestingPerson, PersonStruct{ "Poca","Hontas",24,1.85,Gender::Female });
cout << "New Person attributes: " << endl;
cout << "Name: " << TestingPerson._Name << endl;
cout << "Surname: " << TestingPerson._SurName << endl;
cout << "Age: " << TestingPerson._Age << endl;
cout << "Gender: " << TestingPerson._Gender << endl;
cout << "Heigth: " << TestingPerson._Heigth << endl;
return(0); }
I've made the structure in order to group all Person class parameters. Doing this i've learned that using enum class is more secure than class. But when i switched to enum class a lot of errors prompted on my code. I've solved almost all of them, except this:
cout << "Gender: " << TestingPerson._Gender << endl;
Error code E0349 "no operator "<<" matches these operands"
I've searched around but i find no solution to this. Thanks in advance for your time! (any suggestion or recommendation on my code should be appreciated)
<< operator is not defined for class Gender because it's your own class. You'll need to overload it. More info here.
enum class Gender
{
male,
female
};
ostream& operator<< (ostream & os, const Gender & g)
{
switch(g)
{
case Gender::male: os << "Male"; return os;
case Gender::female: os << "Female"; return os;
}
return os;
};

Why does using my print method with std::cout result in an error?

#include <iostream>
using namespace std;
class Fam
{
public:
char you, urmom, urdad;
void addPerson(char y, char m, char f)
{
you = y;
urmom = m;
urdad = f;
}
};
class Tree: public Fam
{
public:
void showFamtree()
{
cout<< "Name: " << you << endl;
cout<< "Mother's name: " << urmom <<endl;
cout<< "Father's name: " << urdad <<endl;
}
};
int main(void)
{
Tree tree;
char a,b,c;
cin >> a;
cin >> b;
cin >> c;
tree.addPerson(a,b,c);
cout<< "Family tree: " << tree.showFamtree() <<endl;
return 0;
}
I wanted to print the family tree with
the person's name, mother's name, father's name
but when I compile it, I get the following error:
invalid operands to binary expression (basic_ostream<char, std::char_traits<char> > and void)
tree.showFamtree() returns nothing (i.e. void), it doesn't make any sense to try to pass it to std::cout. You might change
cout<< "Family tree: " << tree.showFamtree() <<endl;
to
cout << "Family tree: " << endl;
tree.showFamtree();
If you define operator << like this
ostream& operator << ( ostream & ostr , const Tree & t ){
ostr << "Name:" << t.you << endl
<< "Mother's name:" << t.urmom << endl
<< "Father's name:" << t.urdad << endl;
return ostr;
}
then you can use
cout<< "Family tree: " << tree <<endl;
This is known as operator overloading in C++.
To use something similar to this:
void showFamtree()
{
cout<< "Name: " << you << endl;
cout<< "Mother's name: " << urmom <<endl;
cout<< "Father's name: " << urdad <<endl;
}
with:
cout << "Family tree: " << tree.showFamtree() << endl;
One C++ approach would be to use std::stringstream, as in:
std::string showFamtree()
{
std::stringstream ss;
ss << "Name: " << you << endl;
ss << "Mother's name: " << urmom <<endl;
ss << "Father's name: " << urdad <<endl;
return (ss.str());
}
I also often add a label. So consider using
std::string showFamtree(std::string label)
{
std::stringstream ss;
ss << label;
ss << "Name: " << you << endl;
ss << "Mother's name: " << urmom <<endl;
ss << "Father's name: " << urdad <<endl;
return (ss.str());
}
and change invocation to
cout << tree.showFamtree("Family tree: ") << endl;
Note - Perhaps the label should be on its own line, for consistent white space on the left of the 'tree'.

Hot Dog Stand static function issue

I need this program to create a new HotDogStand object that is able to track how many hot dogs are sold by each stand individually and all together, and I cannot figure out how to make my static method work to find the total number of hot dogs sold between all stands. Can someone point me in the right direction please?
#include <iostream>
using namespace std;
class HotDogStand
{
public:
HotDogStand(int id, int hds);
void justSold();
int getNumSold();
int getID();
int getTotalSold();
private:
int idNum;
int hotDogsSold;
static int totalSold;
};
HotDogStand::HotDogStand(int id, int hds)
{
idNum = id;
hotDogsSold = hds;
return;
}
void HotDogStand::justSold()
{
hotDogsSold++;
return;
}
int HotDogStand::getNumSold()
{
return hotDogsSold;
}
int HotDogStand::getID()
{
return idNum;
}
int HotDogStand::getTotalSold()
{
totalSold = 0;
totalSold += hotDogsSold;
}
int main()
{
HotDogStand s1(1, 0), s2(2, 0), s3(3, 0);
s1.justSold();
s2.justSold();
s1.justSold();
cout << "Stand " << s1.getID() << " sold " << s1.getNumSold() << "." << endl;
cout << "Stand " << s2.getID() << " sold " << s2.getNumSold() << "." << endl;
cout << "Stand " << s3.getID() << " sold " << s3.getNumSold() << "." << endl;
cout << "Total sold = " << s1.getTotalSold() << endl;
cout << endl;
s3.justSold();
s1.justSold();
cout << "Stand " << s1.getID() << " sold " << s1.getNumSold() << "." << endl;
cout << "Stand " << s2.getID() << " sold " << s2.getNumSold() << "." << endl;
cout << "Stand " << s3.getID() << " sold " << s3.getNumSold() << "." << endl;
cout << "Total sold = " << s1.getTotalSold() << endl;
}
Globally (outside of the class), you have to define the static variable:
int HotDogStand::totalSold = 0;
Change
void HotDogStand::justSold()
{
hotDogsSold++;
totalSold++; // increment here
return;
}
And
int HotDogStand::getTotalSold()
{
return totalSold; // just return value
}