delphi - Why does the compiler warn when overloading an abstract method introduced in the base class? -


i have code this:

tbaseclass = class(tobject) protected   procedure amethod(const s:string);virtual;abstract; end;  tderivedclass = class(tbaseclass) protected    procedure amethod(const s:string);overload;override;    procedure amethod(const s:string;const x:integer);overload; end; 

compiler generates warning:

[dcc warning].... w1010 method 'amethod' hides virtual method of base type 'tbaseclass'

clicking on warning sends me 'amethod(const s:string;const x:integer);' since not marked override directive. however, method cannot marked override: no method signature exists in base class, , adding override directive method causes compiler error:

[dcc error].... e2037 declaration of 'amethod' differs previous declaration.

this obvious, since no method signature exists in tbaseclass.

only 'amethod(const s:string)' exists in base class, , method marked 'override' - so nothing in base class being hidden @ all.

why not erroneous warning? (not first 1 i've come across, either...)

the reference other question incorrect, imo. i have solution - used refactor, , renamed problematic method. but i'm not looking solution, trivial. i'm looking explanation of warning. there wrong design? (perhaps using overload , override not design - can agree that, that's not compiler warning about.)

i ran same problem in indy. tidstack base class has abstract getsocketoption() , setsocketoption() methods tidstackbdsbase override , overload own abstract methods descendants (tidstackwindows, etc) override. getting these same kinds of compiler errors.

for example:

type   tidstack = class(tobject)     ...     procedure getsocketoption(asocket: tidstacksockethandle;       alevel: tidsocketoptionlevel; aoptname: tidsocketoption;       out aoptval: integer); virtual; abstract;     ...   end; 

.

type   tidstackbsdbase = class(tidstack)     ...     procedure getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel;       aoptname: tidsocketoption; out aoptval: integer); overload; override;     procedure getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel;       aoptname: tidsocketoption; var aoptval; var aoptlen: integer); overload; virtual; abstract;     ...   end;  procedure tidstackbsdbase.getsocketoption(asocket: tidstacksockethandle;   alevel: tidsocketoptionlevel; aoptname: tidsocketoption; out aoptval: integer); var   lbuf, llen: integer; begin   llen := sizeof(lbuf);   getsocketoption(asocket, alevel, aoptname, lbuf, llen);   aoptval := lbuf; end; 

.

type   tidstackwindows = class(tidstackbsdbase)     ...     procedure getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel;       aoptname: tidsocketoption; var aoptval; var aoptlen: integer); override;     ...   end;  procedure tidstackwindows.getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; var aoptval; var aoptlen: integer); begin   ... end; 

regardless of whether tidstack.getsocketoption() declared overload or not, xe2 reports error:

[dcc error] idstackwindows.pas(296): e2137 method 'getsocketoption' not found in base class 

it turns out in situations (like indy's), compiler requires base class method declared overload (even if there no corresponding overloaded method in base class itself) in order derived class override + overload it.

however, when did that, did not work in xe2 , earlier, causing "hides virtual method" warnings , other errors. appears have been fixed in xe3. ended having in indy was:

  1. declare base tidstack methods overload; virtual; abstract;.

  2. in tidstackbdsbase, declare overriden methods overload; override;, then:

    a. in xe2 , earlier, declare overloaded methods reintroduce; overload;, , declare separate non-overloaded virtual; abstract; methods descendants override.

    b. in xe3 , later, declare overloaded methods overload; virtual; abstract;, , let descendants override them normally.

in other words, following code works in xe3 not in xe2:

type   tidstack = class(tobject)     ...     procedure getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; out aoptval: integer); overload; virtual; abstract;     ...   end; 

.

type   tidstackbsdbase = class(tidstack)     ...     procedure getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; out aoptval: integer); overload; override;     procedure getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; var aoptval; var aoptlen: integer); overload; virtual; abstract;     ...   end;    procedure tidstackbsdbase.getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; out aoptval: integer);   var     lbuf, llen: integer;   begin     llen := sizeof(lbuf);     getsocketoption(asocket, alevel, aoptname, lbuf, llen);     aoptval := lbuf;   end; 

.

type   tidstackwindows = class(tidstackbsdbase)     ...     procedure getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; var aoptval; var aoptlen: integer); override;     ...   end;    procedure tidstackwindows.getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; var aoptval; var aoptlen: integer);   begin     ...   end; 

the following code works in xe2, though:

type   tidstack = class(tobject)     ...     procedure getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; out aoptval: integer); overload; virtual; abstract;     ...   end; 

.

type   tidstackbsdbase = class(tidstack)     ...     procedure wsgetsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; var aoptval; var aoptlen: integer); virtual; abstract;     ...     procedure getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; out aoptval: integer); overload; override;     procedure getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; var aoptval; var aoptlen: integer); reintroduce; overload;     ...   end;  procedure tidstackbsdbase.getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; out aoptval: integer); var   lbuf, llen: integer; begin   llen := sizeof(lbuf);   wsgetsocketoption(asocket, alevel, aoptname, lbuf, llen);   aoptval := lbuf; end;  procedure tidstackbsdbase.getsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; var aoptval; var aoptlen: integer); begin   wsgetsocketoption(asocket, alevel, aoptname, aoptval, aoptlen); end; 

.

type   tidstackwindows = class(tidstackbsdbase)     ...     procedure wsgetsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; var aoptval; var aoptlen: integer); override;     ...   end;    procedure tidstackwindows.wsgetsocketoption(asocket: tidstacksockethandle; alevel: tidsocketoptionlevel; aoptname: tidsocketoption; var aoptval; var aoptlen: integer);   begin     ...   end; 

Comments

Popular posts from this blog

linux - Does gcc have any options to add version info in ELF binary file? -

android - send complex objects as post php java -

charts - What graph/dashboard product is facebook using in Dashboard: PUE & WUE -