Mixin and function template?

renoX renosky at free.fr
Wed Feb 28 15:04:09 PST 2007


Frits van Bommel a écrit :
> renoX wrote:
>> I have a template which contain a single function:
> 
> Let's start with that code...
> 
>> template sputf(A...)
>> {
>>     char[] call()
>>     {
>>         auto fd=std.c.stdio.fopen("tmp_file", "w+");
> 
>>         mixin(`fwritef(fd,`~Fmt!(A)~`);`);   
> 
> This line is equivalent to:
>         fwritef(fd, Fmt!(A));
 > no mixin() required.

In theory yes, in practice when I tried  fwritef(fd, Fmt!(A)); it didn't 
  work..

> 
>>         std.c.stdio.fclose(fd);
>>         auto res = cast(char[])read("tmp_file");
> 
> So basically, you're creating a temporary file, write some formatted 
> output to it, then open it and put the contents in an allocated buffer?
> Why not just:
>         auto res = std.string.format(Fmt!(A));

Because I didn't know this function, thanks for the suggestion.
When I tried it didn't work though, unfortunately..

> That should allocate a string and fill it with with the formatted data. 
> AFAICT it's equivalent to the above code, except the code above creates 
> a file to do it, and so can get into trouble if multiple versions of it 
> get run at the same time from the same directory...
> 
>>         return res;
> 
> Also, you forgot to delete the file before returning. Unless that was 
> intended? (I didn't think so :P)

No, a small mistake.

> 
>>     }
>> }
> 
> So:
> ---
> template sputf(A...)
> {
>     char[] call()
>     {
>         return std.string.format(Fmt!(A));
>     }
> }
> ---
> should be pretty much identical to your code, except for 
> tempfile-related issues in your version.
> 
>> At the call site, I have to do the following:
>>     mixin sputf!("%d{x}") P1;
>>     res = P1.call();
>> which is quite ugly, so I'd like to convert the code in a 'function 
>> template' but when I do this, I don't manage to call the function 
>> without failure..
>> Does someone knows how to do it?
> 
> Well, presumably the function needs to access (local?) variable 'x'. 
> That means you can't avoid using some kind of mixin if you want to do this.

It's not the mixin that I want to get rid of (I can't) but what I'd like 
  is to rename the function call sputf and to have just one function 
call, this works for templates, but not for template function, weird..

> 
> But I don't think the code left in the template is very ugly, so you 
> could also just use it directly, like this:
> ---
> import std.string;
> 
> // ... some stuff here ...
> 
> // example function using Fmt!()
> char[] func(int x) {
>         char[] res = format(Fmt!("%d{x}"));
>     return res;
> }
> ---
> Which is probably cleaner than anything you'll get without:
> a) changing format() to be compile-time executable, or
> b) waiting until Walter sufficiently improves compile-time execution to 
> allow current format() to be usable, or
> c) implementing a compile-time format-like function yourself (either as 
> a compile-time executable function or through template meta programming).

Fmt! is doing c), it is limitated of course because I choose not to 
parse a string and templates do not accept expressions..

The fact that format is not working, nor fwrite(fd but mixin(fwrite(fd 
works make me thing of a bug..

renoX


More information about the Digitalmars-d-learn mailing list