deadalnix wrote:
As all functionnality of a Ship are final, you basically ends up with a mother ship that is a ship and then have some other function that are de facto separated and unreachable from ship.

Yes, because Ship is designed to be the common denominator among Ship types. This is not a problem, it's simply the far right side of access-limitation. There's no need to abstract the type (as you suggest below) simply because the base class went one function "to tight".


Separation of concerns tells us that this should be 2 different objects.

MotherShip is still concerned with being a Ship. It's intended as a Ship, and should be classified as such. Removing the ability to express this only forces coders into needlessly wrapping functions:

  class Ship { final void fire() {} }
  class Bomber : Ship { void bomb() {} }

  void main() {
    auto b = new Bomber();
    b.fire(); // can fire() like other Ships automatically
  }

vs:

  class Bomber {
    Ship ship;
    void fire() { ship.fire(); } // have to wrap this
  }

This would be very annoying if you had many functions in the base class and would probably lead the authors writing a single unused virtual function into the base, just so they could derive types from it.


As teha ddition of MotherShip to Ship are orthogonal, I would argue that mothership functionality is better suited for its own class/struct/whatever, and agregated with a ship.

A Ship wrapper is not conceptually a Ship. Nor could you cast a Ship pointer to it. All you're doing by aggregating types is complicating the structure for no-gain and loosing expression in the process.

Reply via email to