There are two general models describing this situation:
Replacement: "American" school of OOP - child method replaces parent method
Refinement: "Scandinavian" school of OOP - behavior of parent and child classes are merged to form new behavior
If replacement used, then some mechanism usually provided for refinement
If refinement default, then replacement not possible
class SuitPile : public CardPile {
public:
...
virtual int
canTake(Card *);
...
};
// place a single card into a table pile
void TablePile::addCard(Card * aCard)
{ int tx, ty;
// pile is
empty, just place it normally
if (top ==
nilcard)
CardPile::addCard(aCard); // note explicit call
else {
// display it below other cards
tx = top->locx( );
ty = top->locy( );
// figure out where to place card
if (top->faceUp( ) && top->next( ) != nilcard &&
(top->next( ))->faceUp( )) ; // do nothing
else
ty += 30; // move down a bit
CardPile::addCard(aCard); // note explicit call
top->moveTo(tx, ty);
}
Constructors
Always do refinement
class TablePile : public CardPile {
pubic:
TablePile(int,
int, int);
...
private:
int column;
};
TablePile::TablePile(int c, int x, int y) : CardPile(x,
y)
{
column = c;
}
public void addCard (Card aCard) {
cardList.add(aCard); }
...
}
class DiscardPile extends CardPile
{ DiscardPile (int x, int y) { super (x,
y); } // parent's constructor
public void addCard (Card aCard)
{ if (! aCard.faceUp())
aCard.flip();
super.addCard(aCard);
// parent's addCard method
}
...
}