digitalmars.D - Static and non-static method overloading
- Gor Gyolchanyan (108/108) Sep 27 2011 I have a question about static and non-static methods overloading.
- Timon Gehr (4/112) Sep 27 2011 There as been some discussion about this issue and afaik Steve has filed...
- Gor Gyolchanyan (6/145) Sep 27 2011 So, is there any plan to forbid calling static methods from class instan...
- Steven Schveighoffer (6/10) Sep 27 2011 It's an enhancement request, no idea if it will make it in. Feel free t...
I have a question about static and non-static methods overloading. I have this module: -------------------------------------------------------------------------------- /** * Dynamic library interfacing module. */ module dynlib; public: /** * A lazily loaded cached dynamic library. */ class DynLib { public: alias void* Symbol; /** * Loads or returns already loaded dynamic library. */ static DynLib opIndex(in char[] name) { auto lib = name in _libraries; if(lib) return *lib; _libraries[name] = new DynLib(name); return DynLib[name]; } /** * Loads or returns already loaded symbol from this dynamic library. */ Symbol opIndex(in char[] name) { auto sym = name in _symbols; if(sym) return *sym; version(Windows) _symbols[name] = GetProcAddress(_handle, name.toStringz); else version(Posix) _symbols[name] = dlsym(_handle, name.toStringz); return DynLib[name]; } bool empty() property { return _handle is null; } private: alias void* Handle; static DynLib[string] _libraries; static Symbol[string] _symbols; Handle _handle; this(in char[] name) { version(Windows) _handle = LoadLibraryA(name.toStringz); else version(Posix) _handle = dlopen(name.toStringz, RTLD_NOW); } ~this() { version(Windows) FreeLibrary(_handle); version(Posix) dlclose(_handle); } unittest { DynLib dl; version(Windows) dl = DynLib["OpenGL32.dll"]; version(Posix) dl = DynLib["libGL.so"]; assert(!dl.empty); DynLib.Symbol sym = dl["glClearColor"]; assert(sym !is null); } } private: import std.string: toStringz; version(Windows) import core.sys.windows.windows: LoadLibraryA, FreeLibrary, GetProcAddress; else version(Posix) import core.sys.posix.dlfcn: dlopen, dlclose, dlsym; -------------------------------------------------------------------------------- And when i compile this, i get an unexpected error: -------------------------------------------------------------------------------- dynlib.d(24): Error: function dynlib.DynLib.opIndex called with argument types: ((const(char[]))) matches both: dynlib.DynLib.opIndex(in const(char[]) name) and: dynlib.DynLib.opIndex(in const(char[]) name) dynlib.d(39): Error: function dynlib.DynLib.opIndex called with argument types: ((const(char[]))) matches both: dynlib.DynLib.opIndex(in const(char[]) name) and: dynlib.DynLib.opIndex(in const(char[]) name) dynlib.d(39): Error: cannot implicitly convert expression (opIndex(name)) of type dynlib.DynLib to void* -------------------------------------------------------------------------------- My point is: How can this be ambiguous, when i explicitly call the static method from the class name, not the object and when i call a method from an object, the most obvious choice is the non-static one? Cheers, Gor.
Sep 27 2011
On 09/27/2011 05:11 PM, Gor Gyolchanyan wrote:I have a question about static and non-static methods overloading. I have this module: -------------------------------------------------------------------------------- /** * Dynamic library interfacing module. */ module dynlib; public: /** * A lazily loaded cached dynamic library. */ class DynLib { public: alias void* Symbol; /** * Loads or returns already loaded dynamic library. */ static DynLib opIndex(in char[] name) { auto lib = name in _libraries; if(lib) return *lib; _libraries[name] = new DynLib(name); return DynLib[name]; } /** * Loads or returns already loaded symbol from this dynamic library. */ Symbol opIndex(in char[] name) { auto sym = name in _symbols; if(sym) return *sym; version(Windows) _symbols[name] = GetProcAddress(_handle, name.toStringz); else version(Posix) _symbols[name] = dlsym(_handle, name.toStringz); return DynLib[name]; } bool empty() property { return _handle is null; } private: alias void* Handle; static DynLib[string] _libraries; static Symbol[string] _symbols; Handle _handle; this(in char[] name) { version(Windows) _handle = LoadLibraryA(name.toStringz); else version(Posix) _handle = dlopen(name.toStringz, RTLD_NOW); } ~this() { version(Windows) FreeLibrary(_handle); version(Posix) dlclose(_handle); } unittest { DynLib dl; version(Windows) dl = DynLib["OpenGL32.dll"]; version(Posix) dl = DynLib["libGL.so"]; assert(!dl.empty); DynLib.Symbol sym = dl["glClearColor"]; assert(sym !is null); } } private: import std.string: toStringz; version(Windows) import core.sys.windows.windows: LoadLibraryA, FreeLibrary, GetProcAddress; else version(Posix) import core.sys.posix.dlfcn: dlopen, dlclose, dlsym; -------------------------------------------------------------------------------- And when i compile this, i get an unexpected error: -------------------------------------------------------------------------------- dynlib.d(24): Error: function dynlib.DynLib.opIndex called with argument types: ((const(char[]))) matches both: dynlib.DynLib.opIndex(in const(char[]) name) and: dynlib.DynLib.opIndex(in const(char[]) name) dynlib.d(39): Error: function dynlib.DynLib.opIndex called with argument types: ((const(char[]))) matches both: dynlib.DynLib.opIndex(in const(char[]) name) and: dynlib.DynLib.opIndex(in const(char[]) name) dynlib.d(39): Error: cannot implicitly convert expression (opIndex(name)) of type dynlib.DynLib to void* -------------------------------------------------------------------------------- My point is: How can this be ambiguous, when i explicitly call the static method from the class name, not the object and when i call a method from an object, the most obvious choice is the non-static one? Cheers, Gor.There as been some discussion about this issue and afaik Steve has filed a bug report. Currently, it is possible to call a static method on a class instance.
Sep 27 2011
So, is there any plan to forbid calling static methods from class instance or is the bug gonna just fix the ambiguity, while still allowing to call static methods if no appropriate non-static one is available? Cheers, Gor. On Tue, Sep 27, 2011 at 7:23 PM, Timon Gehr <timon.gehr gmx.ch> wrote:On 09/27/2011 05:11 PM, Gor Gyolchanyan wrote:I have a question about static and non-static methods overloading. I have this module: ------------------------------**------------------------------** -------------------- /** * Dynamic library interfacing module. */ module dynlib; public: /** * A lazily loaded cached dynamic library. */ class DynLib { public: alias void* Symbol; /** * Loads or returns already loaded dynamic library. */ static DynLib opIndex(in char[] name) { auto lib = name in _libraries; if(lib) return *lib; _libraries[name] = new DynLib(name); return DynLib[name]; } /** * Loads or returns already loaded symbol from this dynamic library. */ Symbol opIndex(in char[] name) { auto sym = name in _symbols; if(sym) return *sym; version(Windows) _symbols[name] = GetProcAddress(_handle, name.toStringz); else version(Posix) _symbols[name] = dlsym(_handle, name.toStringz); return DynLib[name]; } bool empty() property { return _handle is null; } private: alias void* Handle; static DynLib[string] _libraries; static Symbol[string] _symbols; Handle _handle; this(in char[] name) { version(Windows) _handle = LoadLibraryA(name.toStringz); else version(Posix) _handle = dlopen(name.toStringz, RTLD_NOW); } ~this() { version(Windows) FreeLibrary(_handle); version(Posix) dlclose(_handle); } unittest { DynLib dl; version(Windows) dl = DynLib["OpenGL32.dll"]; version(Posix) dl = DynLib["libGL.so"]; assert(!dl.empty); DynLib.Symbol sym = dl["glClearColor"]; assert(sym !is null); } } private: import std.string: toStringz; version(Windows) import core.sys.windows.windows: LoadLibraryA, FreeLibrary, GetProcAddress; else version(Posix) import core.sys.posix.dlfcn: dlopen, dlclose, dlsym; ------------------------------**------------------------------** -------------------- And when i compile this, i get an unexpected error: ------------------------------**------------------------------** -------------------- dynlib.d(24): Error: function dynlib.DynLib.opIndex called with argument types: ((const(char[]))) matches both: dynlib.DynLib.opIndex(in const(char[]) name) and: dynlib.DynLib.opIndex(in const(char[]) name) dynlib.d(39): Error: function dynlib.DynLib.opIndex called with argument types: ((const(char[]))) matches both: dynlib.DynLib.opIndex(in const(char[]) name) and: dynlib.DynLib.opIndex(in const(char[]) name) dynlib.d(39): Error: cannot implicitly convert expression (opIndex(name)) of type dynlib.DynLib to void* ------------------------------**------------------------------** -------------------- My point is: How can this be ambiguous, when i explicitly call the static method from the class name, not the object and when i call a method from an object, the most obvious choice is the non-static one? Cheers, Gor.There as been some discussion about this issue and afaik Steve has filed a bug report. Currently, it is possible to call a static method on a class instance.
Sep 27 2011
On Tue, 27 Sep 2011 11:38:40 -0400, Gor Gyolchanyan <gor.f.gyolchanyan gmail.com> wrote:So, is there any plan to forbid calling static methods from class instance or is the bug gonna just fix the ambiguity, while still allowing to call static methods if no appropriate non-static one is available?It's an enhancement request, no idea if it will make it in. Feel free to comment: http://d.puremagic.com/issues/show_bug.cgi?id=6579 -Steve
Sep 27 2011