On Fri, 27 May 2011 02:34:34 -0400, Matthew Ong <on...@yahoo.com> wrote:
Hi All,
Currently within D, to make use of a parent class method you have to do:
class Parent{
void methodA(int x){...}
}
class Child : Parent{
// I understand that it has to do with preventing accidental
hijacking
alias Parent.methodA methodA;
void methodA(long x){...}
}
void main(string[]){
Child obj=new Child();
obj.methodA(1); // expecting to call Child.methodA but calling
Parent.methodA;
}
and also from this URL.
http://www.digitalmars.com/d/2.0/function.html
If, through implicit conversions to the base class, those other
functions do get called, an std.HiddenFuncError exception is raised.
-----------------------------------------------------------------------
That is to prevent silently changing the program's behavior. b.foo(1)
could happily be a call to B.foo(long) today. Imagine one of the base
classes changed and now there is A.foo(int). Then our b.foo(1) would
silently start calling that new function. That would cause a tough bug.
Ali // a Better explanation than the document for the current syntax.
------------------------------------------------------------------------
However, there is a foreseeable problem coming when a program grow.
How about when the inheritance tree becomes deeper than 4? And more and
more overloaded functions are in different classes? That does not meant
the calling class/method has a sense if it is calling from Child or
Parent. Because, those 2 classes source code might not be available for
coder. How does the coder knows about that?
Does it mean we have to do more alias at child class at the bottom?
Harder to issues solve in the child class at the bottom of the tree.
It seem to me that the entire purpose is just to protect auto promotion
matching method signature in the base to avoid function hijacking.
How about doing this another way? Just a suggestion if you like to avoid
parent function from accidental hijack but still needs to be public. New
keywords are needed: nooverload and inheritall
class Parent{
nooverload void methodA(int x){...} // entirely deny this name to
be overloaded.
}
// this would have avoided the aliasing all over child class and still
allow child class to see any >public< method of the parent.
class Child: inheritall Parent{ // auto inheriting all parent methods
except private ones. As per usual also for package/protected...
void methodA(long x){...} // compilation error. because nooverload
is used at Parent
void methodA(string x){...} // compilation error. because nooverload
... etc
void methodB(){
methodA(123); // No error now, and the entire hijacking is
avoided.
}
}
void main(string[] args){
Child obj=new Child();
obj.methodB(); // no problem
obj.methodA(123); // no accidental hijacking...Always use parent
class.
}
Reverse sequence as Ali has shown can also be avoided because if someone
does that by adding 'new' methodA in parent where child already has
methodA overloaded already without knowledge. Show up in compilation
exception for such cases with -w flag on.
How about that? Possible solution?
I don't think it will work that well. Consider how function hijacking
happens. For instance, the parent class author may not even know his code
is being overridden, and he may simply not mark his base function as
nooverload. Let's say that the child is inheriting all the parent's
methods because he wanted a different method (an already existing one),
and the author of the parent class adds methodA (without the nooverload
attribute) after the child is already written. That's an unintentional
hijack. The problem is the child is relying on the parent to cooperate in
preventing hijacking, instead of controlling whether its functions can be
hijacked or not.
In the current solution, the system warns me or throws an error if a
function becomes hijacked. If this happens, I can examine the code and
add an alias if needed. It happens rarely for me. Do you have cases
where you have to "alias all over the place"? Maybe you are not doing
something correctly, you shouldn't need this feature all the time.
Note that drastic proposals like this are very unlikely to be accepted.
Especially for something that has been in use and not really complained
about for years. You need to present a very compelling argument,
including real examples is helpful. Also, if there's any way to get rid
of adding a keyword, you have a much better shot of success. No keywords
have been added to the language for a long time.
-Steve