问题
If i have these 3 interfaces
unit Interfaces;
interface
type
IA = interface['{86367399-1601-4FDD-89CF-362E762D948E}']
procedure doSomething;
end;
IB = interface['{070B9364-4A57-4E5A-BBA7-FBF1C6A48C5A}']
procedure doSomething;
end;
IC =interface(IB)['{DAC8021C-42CB-40EC-A001-466909044EC3}']
procedure doSomething;
end;
implementation
end.
How do i resolve naming conficts in a class that implements IA and IC? I have no problem with IA and IC but how do i implement IB?
type
myClass = class(TInterfacedObject, IA, IC)
procedure doASomething;
procedure doBSomething;
procedure doCSomething;
procedure IA.doSomething = doASomething;
// ??? = doBSomething;
procedure IC.doSomething = doCSomething;
end;
回答1:
Your class doesn't implement IB. So there's no way to use a method resolution clause for an interface that is not implemented by that class. So, you might imagine that the easy way out is to implement that interface:
type
myClass = class(TInterfacedObject, IA, IB, IC)
procedure doASomething;
procedure doBSomething;
procedure doCSomething;
procedure IA.doSomething = doASomething;
procedure IB.doSomething = doBSomething;
procedure IC.doSomething = doCSomething;
end;
But this fails to compile also. The error is:
[dcc32 Error]: E2291 Missing implementation of interface method IB.doSomething
I conclude that there is no way for you to implement these interfaces directly. I think that the only way you could square this particular circle would be to use an implements clause to delegate implementation. For instance:
type
myClass = class(TInterfacedObject, IA, IB, IC)
private
FA: IA;
FB: IB;
FC: IC;
property A: IA read FA implements IA;
property B: IB read FB implements IB;
property C: IC read FC implements IC;
end;
Obviously you'd need to initialise the fields FA, FB and FC, but I leave that as an exercise for you.
This isn't a very satisfactory solution. If I were in your place, I'd be looking very hard for a solution that avoided the name clashes in the first place.
回答2:
As per my comment:
Does it really make sense for an extension of IB (namely IC) to redeclare an identical method? Since IC extends IB, procedure doSomething; is already available. As a client using an implementation of IC, how would you call IC's doSomething differently from IB's doSomething?
So if you do the following, you should have no trouble.
IC =interface(IB)['{DAC8021C-42CB-40EC-A001-466909044EC3}']
//procedure doSomething; //Don't redeclare an existing method in an extension.
end;
type
myClass = class(TInterfacedObject,
//Explicitly state that you're implementing IB
IA, IB, IC)
procedure doASomething;
procedure doBSomething;
procedure doCSomething;
procedure IA.doSomething = doASomething;
//And you'll be able to define IB's method resolution.
procedure IB.doSomething = doBSomething;
procedure IC.doSomething = doCSomething;
end;
You may also find some of the information in this question and answers useful, as it discusses why you need to explicitly state which interfaces a class implements.
来源:https://stackoverflow.com/questions/28582426/resolve-naming-conflicts-caused-by-interface-inheritance-in-delphi