Non-Virtual Interfaces

Jonathan M Davis jmdavisProg at gmx.com
Fri Mar 4 11:20:57 PST 2011


On Friday, March 04, 2011 02:17:00 Aleksandar Ružičić wrote:
> I'm trying to use NVI idiom but i keep getting errors from dmd.
> 
> This is my setup:
> 
> module test;
> 
> import std.stdio;
> 
> interface IBase {
> 	void foo();
> 	void bar();
> }
> 
> interface IBar : IBase {
> 	final void bar() {
> 		writefln("IBar.bar()");
> 	}
> }
> 
> class Foo : IBar {
> 
> 	void foo() {
> 		writefln("Foo.foo()");
> 	}
> }
> 
> void main() {
> 
> 	Foo foo = new Foo();
> 	foo.foo();
> }
> 
> When I try to compile it i get "test.d(16): Error: class test.Foo
> interface function IBar.bar isn't implemented"
> 
> And if I try to define bar() in Foo i receive "test.d(22): Error:
> function test.Foo.bar cannot override final function
> IBar.test.IBar.bar"
> which is expected since IBar.bar() is final.
> 
> So, am I missing some point about NVIs here or is it just not yet
> implemented in dmd?

In NVI, you have a public, non-virtual function which calls a private one which 
is then overridden by a derived class (or in this case, a class which implements 
the interface). So, the API is non-virtual, but the functionality is overridden. 
It gives you the ability to enforce that certain things happen when the function 
is called (such as checking something about the parameters or enforcing that a 
set of functions are always called in a particular order), but the actual 
functionality is still overridden.

In D, the public function would have to be final to make it non-virtual/non-
overridable, and the function it calls would have to be protected, since you 
can't override private functions ( 
http://d.puremagic.com/issues/show_bug.cgi?id=4542 ). In this case, you're 
trying to override final functions, which doens't work at all.

However, if you're not trying to do anything other than call the implemented 
function (you're certainly not here), then there's no point to NVI. Just use a 
normal, public interface function or make the base class of your class abstract 
and put the function's declaration there.

- Jonathan M Davis


More information about the Digitalmars-d-learn mailing list