1

I have Class A as a base class , and Class B , C derived classes from A and there's class D who have a data member (pointer to Array) of type A (Composition)

enter code here

class D{
A **a;
int size;
.......
a = new A*[size]; 
......
 };

and i have Print method , in its body i have to specific element (if it from class B or C ) with a given ID(both B and C have a data member ID ) there should be 2 options in print function .. printing elements for class B , or printing elements for class C ? how can i specific the elements ?

i made class A abstract!!

enter code here
class A{
.......
virtual void print ()=0;
};

class B :public A{
........
........
void print(){
.......}
};

class C :public A{ ........ ........ void print(){ .......} };

class D{
........
.......
void Print ()
int P;
cout<<" if you want to print class B elements enter 1 , or 2 for class C"<<endl;
cin>>P;
if(P==1){
dynamic_cast<B*>(*a)->print(); }
else
if (P== 2){
 dynamic_cast<C*>(*a)->print(); }

my Question here is how can i specific the elements if it from class B or C ???

Rai Ou
  • 15
  • 6

1 Answers1

2

I'm assuming a couple of things here, in particular that the a member actually contains pointers to subclasses of A -- that is, Bs and Cs.

I'm also assuming that in the print method as you're iterating through this array you don't know which is which.

If you don't care which is which and simply want to print attributes of the object no matter what type they are, then you could provide a pure virtual method in A which returns a std::string (or something) that you want to print(), and call that method in your iteration:

class A
{
public:
  virtual std::string printMe() const = 0;
};

class B : public A
{
public:
  std::string printMe() const { return "I'm a B"; }
};

class C : public A
{
public:
  std::string printMe() const { return "I'm a C"; }
};

If you only want to print objects of either type B or C, then you'll need to be able to determine which is which using dynamic_cast. Since using dynamic_cast in this way only works with polymorphic types, you need to ensure that A has at least 1 virtual function. However this is OK because, since A is being used in an abstract hierarchy, you really should have a virtual destructor anyway, and that is enough.

class A
{
public:
  virtual ~A() {};
};

Now you can use dynamic_cast:

void A::print()
{
  for (size_t i = 0; i < size; ++i)
  {
    A* theObj = a[i];
    // assuming we only want to print B's...
    B* theB = dynamic_cast <B*> (theObj);
    if (theB)
    {
      theB->printObj();
    }
  }
}
Community
  • 1
  • 1
John Dibling
  • 99,718
  • 31
  • 186
  • 324
  • Your class B printMe returns "I'm an A" which is true, but you might mean "I'm a B". Your class C printMe returns "I'm a B" which is not true and should be "I'm a C" – YoungJohn Dec 20 '13 at 15:17
  • @JohnDibling thank u so much , but the print in class A is "virtual void print ()=0;" , and i override it in B and C , my Question here is how can i specific the elements if it's from class B or C in print of class **D** ?? – Rai Ou Dec 20 '13 at 16:11
  • @RaiOu: OK, use my answer simply as a guide to solving your actual problem. – John Dibling Dec 20 '13 at 16:13