// pointers to base class
#include <iostream>
using namespace std;

class CPolygon {
  protected:
    int width, height;
  public:
    void set_values (int a, int b)
      { width=a; height=b; }
  };

class CRectangle: public CPolygon {
  public:
    int area ()
      { return (width * height); }
  };

class CTriangle: public CPolygon {
  public:
    int area ()
      { return (width * height / 2); }
  };

int main () {
  CRectangle rect;
  CTriangle trgl;
  CPolygon * ppoly1 = &rect;
  CPolygon * ppoly2 = &trgl;
  ppoly1->set_values (4,5);
  ppoly2->set_values (4,5);
  cout << pploy1->area() << endl;
  cout << ppoly2->area() << endl;
  return 0;
}

I have a question with the above code.
ppoly1->set_values (4,5);
ppoly2->set_values (4,5);
works and successfully set values for rect and trgl but
cout << pploy1->area() << endl;
cout << ppoly2->area() << endl;
doesn't work, why? I think if
ppoly1->set_values (4,5);
ppoly2->set_values (4,5);
works means *ppoly1 and *ppoly2 can represent derived classes, so we can access the derived class area functions by using pploy1->area() and pploy2->area()
but the compiler shows errors

thanks

Edited 6 Years Ago by tennis: n/a

#1 you misspelled ppoly1 in cout << pploy1->area() << endl; so that should be giving you an error.

In order for the code to work the way you want it to you would need to make a pure virtual function in the class CPolygon: virtual int area() = 0; By doing this you cannot have an instance of CPolygon because it has a pure virtual function but you are allowed to have pointers to that class type or of a class that inherits CPolygon (ie CRectangle or CTriangle).

Right now it is trying to find that function in the CPolygon class and it doesn't exist so you cannot do it.

What you are looking for is polymorphism. This example should answer your question :

struct Polygon{
 int width,height;
 virtual int area()const = 0;
};
struct Rect : Polygon{
 int area()const{ return width * height; }
};
struct Triangle : public Polygon{
 int area()const{ return width*height*0.5f; }
}

//notice input could be any class that derives from Polygon class
void printArea(const Polygon& p){
 cout << p.area() << endl;
}
int main(){
 Rect r;
 r.width = 5;
 r.height = 5;

 Triangle t;
 t.width = 6;
 t.height = 3;
 
 printArea(r); 
 printArea(t);
}


Right now it is trying to find that function in the CPolygon class and it doesn't exist so you cannot do it.

Thanks for the reply.
So you mean pploy1->area() and pploy2->area() are in the base class.
But how can
ppoly1->set_values (4,5);
ppoly2->set_values (4,5);
successfully set value for the derived classes. Based on what you said, these two are also in base class?

Funny thing is that when I saw his code I knew it was from here and it is under the section Polymorphism. If you read on a bit it goes into all the virtual functions and all that so finish the section and it will make more sense.

ppoly1 is a pointer to a CPolygon.
The class CPolygon does not have an area() function so if you try to call that directly it will error.
You can call the function set_values(int, int) because in the CPolygon class that function exists.
You can point to rect or trgl because they are built off of the CPolygon class (they are CPolygon plus whatever you add to it in the new class).
This means that you can call functions with a higher class (CRectangle) from a lower class (CPolygon) but not the other way around unless they are defined virtually.

Edited 6 Years Ago by sfuo: wording was wrong

thanks for the reply
I think my real confusion is

#include <iostream>
using namespace std;

class CPolygon {
public: 
int width, height;
void set_values (int a, int b)
  { width=a; height=b; }
  };

class CRectangle: public CPolygon {
  public:
  int area ()
  { return (width * height); }
  };

class CTriangle: public CPolygon {
  public:
  int area ()
  { return (width * height / 2); }
  };

int main () {
  CRectangle rect;
  CTriangle trgl;
  CPolygon * ppoly1 = &rect;
  CPolygon * ppoly2 = &trgl;
  ppoly1->set_values (4,5);
  cout<<rect.width;

  return 0;
}

since set_values is not virtual function so ppoly1->set_values (4,5); should be static binding, so it should set_values in base class, but why cout<<rect.width; is 4?
One may say because the derived class inherited the base class value of 4, but
cout<<trgl.width<<endl; is -858993460

Edited 6 Years Ago by tennis: n/a

Because ppoly1 points to rect and ppoly2 points to trgl.

These are two separate instances of the class and what happens to one only happens to that class unless you were to set the width to a static int then it would change for all instances of that class.

This article has been dead for over six months. Start a new discussion instead.