caller trouble

Jonathan M Davis jmdavisProg at gmx.com
Sat Jul 14 00:12:55 PDT 2012


On Saturday, July 14, 2012 01:53:34 captaindet wrote:
> i need a discreet handle on the calling/instantiating source file (module).
> using __FILE__, it is surprisingly easy for functions (via argument) and
> templated functions (via template parameter) but i cannot get it working
> for templated classes. how can i make them aware of the calling module?
> 
> thx, det
> 
> 
> module other;
> 
> string fun(string infile = __FILE__){ return infile; }
> string tfun(string infile = __FILE__)(){ return infile; }
> class tclass(string infile = __FILE__){ string from = infile; }
> 
> //...//
> 
> module main;
> import other;
> 
> void main(){
>      auto _fun = fun();			//_fun == "main.d"
>      auto _tfun = tfun();		//_tfun == "main.d"
>      auto _tclass = new tclass!();	//_tclass.from == "other.d" !!!
> 
>      //this works but i do not want to provide __FILE__ explicitly:
>      auto _tclassx = new tclass!(__FILE__)();	//_tclass.from == "main.d"
>      //and why do i get 2 different results for the last 2 cases?
> }

I believe that __FILE__ and __LINE__ are treated specially with functions in 
order for them to be filled in at the call site rather than the declaration 
site. If it's not working with classes, then that probably means that whatever 
special logic was done to make them work with functions was only done for 
functions. If you want, you can open an enhancement request:

http://d.puremagic.com/issues

However, I would point out that that would mean that every single module which 
uses tclass would end up with a different and incompatible instantiations of 
tclass, so if __FILE__ worked with class templates like you want it to, then 
any such class wouldn't work outside of the module that it was constructed in 
save for code that uses auto and typeof to get the type. And I have hard time 
believing that that would be a good idea.

With a templated function, it doesn't really matter if two different call 
points end up with different instantiations. They'll both work just fine. But 
having a class which only works in the module where it's instantiated would be 
_far_ more limiting.

However, if you _really_ want something like this, you can always just wrap 
the creation of the object in a function:

auto create(string infile = __FILE__, Args...)(Args args) { return new 
tclass!infile(args); }

Args isn't necessary if there are no arguments for the constructor, but it 
_is_ if there are, and it'll work if there aren't.

- Jonathan M Davis


More information about the Digitalmars-d-learn mailing list