Named Inheritance
Research: This page describes research about Eiffel, not the actual language specification.
Motivation:
- Remove the need for adapter classes.
- Reconcile the relatively loose conventions around agents in to the more strict conventions of inheritance.
Similarity between adapter classes and agents
Take the starting classes A and B:
class A feature process_1 do -- Operate on value_1 end value_1: INTEGER test_1: BOOLEAN process_2 do -- Different operation on value_2 end value_2: INTEGER test_2: BOOLEAN end
deferred class B feature process deferred end value: INTEGER deferred end test: BOOLEAN deferred end end
And adapters C and D:
class C inherit B feature make (sourceA: A) do source := sourceA end source: A process do source.process_1 end value: INTEGER do result := source.process_1 end test: INTEGER do result := source.test_1 end end
class D inherit B feature make (sourceA: A) do source := sourceA end source: A process do source.process_2 end value: INTEGER do result := source.value_2 end test: BOOLEAN do result := source.test_2 end end
Using these adapters, if A wanted to provide clients access to itself in 2 different ways through B, the following features could be added to A:
class A --Same features as above-- feature one: B do result := create {C}.make (current) end two: B do result := create {D}.make (current) end end
Another way A could provide access to itself similar to B is by use of agents:
class A --Same features as above-- feature one: TUPLE [process: PROCEDURE [ANY, []], value: FUNCTION[ANY, [], INTEGER], test: FUNCTION[ANY, [], BOOLEAN]] do result.process := agent process_1 result.value := agent value_1 result.test := agent test_1 end two: TUPLE [process: PROCEDURE [ANY, []], value: FUNCTION[ANY, [], INTEGER], test: FUNCTION[ANY, [], BOOLEAN]] do result.process := agent process_2 result.value := agent value_2 result.test := agent test_2 end end
Disadvantages of adapters:
- Requires 1 new class for every way a class wishes to provide facilities to clients.
Disadvantages of agents:
- Requires a new, though already implemented, language construct `agents'.
- Strongly typed contracts related to agents are not defined.
Implementation of A using named inheritance:
class A inherit one: B rename process as process_1, value as value_1, test as test_1 end two: B rename process as process_2, value as value_2, test as test_2 end feature process_1 do -- Operate on value_1 end value_1: INTEGER test_1: BOOLEAN process_2 do -- Different operation on value_2 end value_2: INTEGER test_2: BOOLEAN end
A client of A could make use of the named inheritance functionality as such:
class APPLICATION feature make local obj: A one: B two: B do create obj one := obj.one two := obj.two end end