Re: Determining if a class has a template function
On Friday, 14 October 2016 at 09:15:40 UTC, Marc Schütz wrote: On Wednesday, 12 October 2016 at 16:57:50 UTC, Meta wrote: There's also a *very* ugly hack you can do: //A template function's .stringof is of the format name>()() //so match on the number of brackets to determine whether it's a template function or not enum isTemplateFunction = __traits(isTemplate, f) && fstr.balancedParens('(', ')') && (fstr.canFind("if") || fstr.count!(c => cast(bool)c.among!('(', ')')) == 4); This won't work if there are additional parens _inside_ compile/runtime parameters, though, which there is ample opportunity for: T func(T : U!(int, string), U)(const(T) param = defaultValue!(const(T))()); You're right... And this is why it's such an ugly hack. It can probably be improved upon but I would not recommend trying, although there's no other way I can think of to determine whether a template is a function template.
Re: Determining if a class has a template function
On Wednesday, 12 October 2016 at 16:57:50 UTC, Meta wrote: There's also a *very* ugly hack you can do: //A template function's .stringof is of the format name>()() //so match on the number of brackets to determine whether it's a template function or not enum isTemplateFunction = __traits(isTemplate, f) && fstr.balancedParens('(', ')') && (fstr.canFind("if") || fstr.count!(c => cast(bool)c.among!('(', ')')) == 4); This won't work if there are additional parens _inside_ compile/runtime parameters, though, which there is ample opportunity for: T func(T : U!(int, string), U)(const(T) param = defaultValue!(const(T))());
Re: Determining if a class has a template function
On Wednesday, 12 October 2016 at 16:57:50 UTC, Meta wrote: //A template function's .stringof is of the format name>()() //so match on the number of brackets to determine whether it's a template function or not enum isTemplateFunction = __traits(isTemplate, f) && fstr.balancedParens('(', ')') && (fstr.canFind("if") || fstr.count!(c => cast(bool)c.among!('(', ')')) == 4); Whoops, I forget to say that fstr is defined like this: enum fstr = f.stringof;
Re: Determining if a class has a template function
On Wednesday, 12 October 2016 at 16:29:22 UTC, Basile B. wrote: On Tuesday, 11 October 2016 at 20:17:19 UTC, Straivers wrote: I have a class T with a templated function foo(string name)(int, int, float) that will be mixed in via template, and I want to determine if that class has mixed it in such that foo(name = "bar"). How could I go about this? Thanks. eg: mixin template A(string name, Args...) { void foo(string fooName)(Args args) if (fooName == name) {} } template hasFoo(string name, A) { enum hasFoo = ??? } class B { mixin A!("mash", int, int, string); } For this particular example the following solution works: template A(string name, Args...) { void foo(string fooName)(Args args) if (fooName == name) {} } template hasFoo(string name, T, V...) { enum hasFoo = __traits(hasMember, T, "foo") && is(typeof(T.foo!name) == typeof(A!(name,V).foo!name)); } class B { mixin A!("mash", int, int, string); } unittest { static assert( hasFoo!("mash", B, int, int , string)); static assert( !hasFoo!("rash", B, int, uint , string)); } Now I can't say that I's generic enough to validate any members that's injected. Note well that it wouldn't work with a regular mixin template. You can also take a look at "std.traits.TemplateOf" There is also isTemplate (https://dlang.org/spec/traits.html#isTemplate). You can check first that the member exists and then check if it's a template (though this will pick up more than just template functions). There's also a *very* ugly hack you can do: //A template function's .stringof is of the format name>()() //so match on the number of brackets to determine whether it's a template function or not enum isTemplateFunction = __traits(isTemplate, f) && fstr.balancedParens('(', ')') && (fstr.canFind("if") || fstr.count!(c => cast(bool)c.among!('(', ')')) == 4);
Re: Determining if a class has a template function
On Tuesday, 11 October 2016 at 20:17:19 UTC, Straivers wrote: I have a class T with a templated function foo(string name)(int, int, float) that will be mixed in via template, and I want to determine if that class has mixed it in such that foo(name = "bar"). How could I go about this? Thanks. eg: mixin template A(string name, Args...) { void foo(string fooName)(Args args) if (fooName == name) {} } template hasFoo(string name, A) { enum hasFoo = ??? } class B { mixin A!("mash", int, int, string); } For this particular example the following solution works: template A(string name, Args...) { void foo(string fooName)(Args args) if (fooName == name) {} } template hasFoo(string name, T, V...) { enum hasFoo = __traits(hasMember, T, "foo") && is(typeof(T.foo!name) == typeof(A!(name,V).foo!name)); } class B { mixin A!("mash", int, int, string); } unittest { static assert( hasFoo!("mash", B, int, int , string)); static assert( !hasFoo!("rash", B, int, uint , string)); } Now I can't say that I's generic enough to validate any members that's injected. Note well that it wouldn't work with a regular mixin template. You can also take a look at "std.traits.TemplateOf"