On Friday, 2 August 2013 at 11:48:32 UTC, Andrej Mitrovic wrote:
On Friday, 2 August 2013 at 11:37:27 UTC, Bosak wrote:
I want to create a mixin template such that:

mixin template ArgNull(alias arg, string name)
{
   if(arg is null)
       throw new Exception(name~" cannot be null.");
}

But is there a way to do that with only one template argument. And then use it like:

string text = null;
mixin ArgNull!(text);

And the above mixin to make:

if(text is null)
   throw new Exception("text cannot be null.");

Note that template mixins cannot inject arbitrary code, they can only inject declarations. You can use '__traits(identifier, symbol)' on an alias parameter to retrieve the symbol name, for example:

-----
mixin template ArgNull(alias arg)
{
    void test()
    {
        if (arg is null)
throw new Exception(__traits(identifier, arg) ~ " cannot be null.");
    }
}

string text = null;
mixin ArgNull!text;

void main()
{
    test();
}
-----

I ended up with the following code:

string ArgNull(string arg)() {
return "if("~arg~" is null)throw new Exception(\""~arg~" cannot be null.\");";
}

unittest {
    import std.exception;

    void foo(Object obj, string str)
    {
        mixin(ArgNull!"obj");
        mixin(ArgNull!"str");
    }

    assertThrown(foo(null, ""));
    assertThrown(foo(new Object, null));
    assertNotThrown(foo(new Object, ""));
}

It does what I wanted it to. Is there a better way to do it? Or do you have any suggestions on my code? I am kind of new to D and all this template and mixin stuff.

Reply via email to