Variadic template arguments unpacking
Max Strakhov
monnoroch at gmail.com
Sat Jul 6 12:39:32 PDT 2013
> foo(getArray(v[0])[], getArray(v[1])[], getArray(v[2])[]);
>
> It's easy to conceptualise and easy to get it right.
I wrote a template, that can do something like that:
template Expand(string code, string Args, string args, Ts...) {
const hasType = std.string.indexOf(code, "%Arg") != -1;
const hasVal = std.string.indexOf(code, "%arg") != -1;
static if(hasType)
const code1 = std.array.replace(code, "%Arg", Args ~ "[%d]");
else
const code1 = code;
static if(hasVal)
const code2 = std.array.replace(code1, "%arg", args ~ "[%d]");
else
const code2 = code1;
template Fun(size_t i, T) {
static if(!hasType && !hasVal)
alias Fun = TypeTuple!(code2);
else static if(hasType && hasVal)
alias Fun = TypeTuple!(std.string.format(code2, i, i));
else
alias Fun = TypeTuple!(std.string.format(code2, i));
}
template ConcatArgs() {
const Val = "";
}
template ConcatArgs(T, As...) if(!is(T == string)) {
static assert(T);
}
template ConcatArgs(string s, As...) if(As.length == 0) {
const Val = s;
}
template ConcatArgs(string s, As...) if(As.length != 0) {
const Val = s ~ ", " ~ ConcatArgs!As.Val;
}
const Val = ConcatArgs!(staticIndexedMap!(Fun, Ts)).Val;
}
Usage:
writeln(Expand!("getArray(%arg)[]", "", "v", string, int,
int).Val); // == getArray(v[0])[], getArray(v[1])[],
getArray(v[2])[]
If anyine has any ideas how make this implementation simplier,
bring it on :)
More information about the Digitalmars-d-learn
mailing list