On 05/05/2016 11:08 PM, Dicebot wrote: > Unless parameter list is very (very!) long, I'd suggest to simply copy > it into a stack struct. Something like this: > > auto toInputRange (T...) (T args) > { > struct Range > { > T args; > size_t index; > > T[0] front () { return args[index]; } > void popFront () { ++index; } > bool empty () { return index >= args.length; } > } > > return Range(args, 0); > }
I wanted this syntax to work but when I tested I saw that T does not expand to struct members.
I like Alex Parrill's only() solution but it allocates a dynamic array as well by doing the equivalent of [args] in the guts of its implementation.
As Dicebot said, unless there are tons of arguments, I think the following is the best as it is @nogc. It executes a switch statement for each front() call though. And I like the CommonType!T idea there.
import std.stdio; import std.string; /* Support empty Args? */ @nogc pure nothrow auto toInputRange(Args...)() { struct Range { size_t index; bool empty() { return index >= Args.length; } void popFront() { ++index; } import std.traits : CommonType; alias E = CommonType!Args; E front() { final switch (index) { /* static */ foreach (i, arg; Args) { case i: return arg; } } } } return Range(); } unittest { import std.traits; import std.range; static assert(isInputRange!(ReturnType!(toInputRange!(1)))); } void main() { auto r = toInputRange!(1, 2.5, 3); writeln(r); } Ali