inheritanced

Calling overloaded parent methods from child class in D


Suppose I have the following D code:

class Parent {
    void print(int x) {
        import std.stdio : writeln;
        writeln(x);
    }

    abstract void print(string s);
}

class Child : Parent {
    override void print(string s) {
        import std.stdio : writeln;
        writeln(s);
    }
}

unittest {
    Child c = new Child();
    c.print(5);
}

When I compile this code, I get a compiler error stating that

function Child.print(string s) is not callable using argument types (int)

This is confusing, because I would expect that the parent's print(int x) method would be invoked when calling it on the child. I can solve this casting inline, like (cast(Parent)c).print(5), but this seems awkward.

Is this a bug in the language? Or is there a better approach to inheritance with overloaded methods?


Solution

  • You'll need to modify Child with an alias to Parent.print:

    class Child : Parent {
      
        alias print = Parent.print;
    
        override void print(string s) {
            import std.stdio : writeln;
            writeln(s);
        }
    }
    

    This is intentional. It's to prevent function hijacking. You can read about it here: https://dlang.org/articles/hijack.html

    The relevant text from the section 'Derived Class Member Function Hijacking':

    C++ has the right idea here in that functions in a derived class hide all the functions of the same name in a base class, even if the functions in the base class might be a better match. D follows this rule. And once again, if the user desires them to be overloaded against each other, this can be accomplished in C++ with a using declaration, and in D with an analogous alias declaration.