Mixin and function template?
renoX
renosky at free.fr
Thu Mar 1 13:12:16 PST 2007
Hasan Aljudy a écrit :
>
>
> renoX wrote:
>> Hello,
>>
>> I have a template which contain a single function:
>> template sputf(A...)
>> {
>> char[] call()
>> {
>> auto fd=std.c.stdio.fopen("tmp_file", "w+");
>> mixin(`fwritef(fd,`~Fmt!(A)~`);`);
>> std.c.stdio.fclose(fd);
>> auto res = cast(char[])read("tmp_file");
>> return res;
>> }
>> }
>> 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?
>>
>> Regards,
>> renoX
>
>
> I wrote some code so that you could print local variables or expressions
> by wrapping them with {{ double braces }} inside the string (this is a
> Django idiom).
Thanks for your code, the syntax I used is inspired from Ruby #{} except
that I thought that in printf '%' is the escape char, that's why I'm
using %s{} or %d{} (and %{ as equivalent to '{')
We're doing more or less the same thing, except that my implementation
takes a tuple instead of just one string which allows to be a little bit
compatible with printf: mixin(putf!("%d",x)) works.
But I have a hard time making the equivalent of for format/sprintf..
renoX
>
> The code is not so stable as it doesn't do anything about escaping and
> stuff .. and it's not really tested at all .. except for one use-case;
> it's the intended typical usage:
>
> auto name = "hasan";
> mixin( bang( "hello {{name}}, how are you?" ) );
>
> the idea is to replace bang("string1 {{expr}} string2") with
> writefln( "string1", expr, "string2" );
>
> Here's the code, it's written in an ugly aggressive way because it was
> my first attempt to play with mixins & compile-time functions, so I
> stayed as low-level as possible.
> ------------
> import std.stdio;
>
> char[] parse( char[] string )
> {
> char[] result = "";
> int index = 0;
> while( index < string.length )
> {
> //scan for {{
> bool sequence = false;
> int start = index;
> while(index < string.length)
> {
> if( (index < string.length-2) )
> {
> if( (string[index] == '{') && (string[index+1] == '{') )
> {
> sequence = true;
> break;
> }
> }
> index++;
> }
> auto raw = string[start..index]; //this holds the contents of
> string up to the first "{{" if there is one.
>
> if( result.length > 0 )
> result = result ~ ", ";
> result = result ~ `"` ~ raw ~ `"`;
>
> if( sequence )
> {
> index+= 2;
> start = index;
> //look for }}
> while( (index < string.length-2) )
> {
> if( (string[index] == '}') && (string[index+1] == '}') )
> break;
> index++;
> }
> auto exp = string[start..index];
> result = result ~ ", " ~ exp;
> index += 2;
> }
> }
>
> return result;
> }
>
> char[] bang( char[] expr )
> {
> expr = parse(expr);
> return `writefln(` ~ expr ~ `);`;
> }
>
> void main()
> {
> auto name = "hasan";
> mixin( bang( "hello {{name}}, how are you?" ) );
> }
> ----------
>
More information about the Digitalmars-d-learn
mailing list