On Tue, Oct 12, 2010 at 02:33, Andrei Alexandrescu <[email protected]> wrote:
> ElementType!R1[] join(R1, R2)(R1 items, R2 sep) > if (isInputRange!R1 && isForwardRange!R2 > && is(ElementType!R2 : ElementType!R1); > Notice how the separator must be a forward range because it gets spanned > multiple times, whereas the items need only be an input range as they are > spanned once. This is at the same time a very general and very precise > interface. I like this and I've nothing against this signature, but I'm probably biased. When I look at this, I don't even look for the function name: the constraints (ie, the interface) is what catches my eye. > One thing is still bothering me: the array output type. Why would the > "default" output range be an array? What can be done to make join() at the > same time a general function and also one that works for strings the way the > old join did? For example, if I want to join things into an already-existing > buffer, or if I want to write them straight to a file, there's no way to do > so without having an array allocation in the loop. I have a couple of ideas > but I wouldn't want to bias yours. Let to my own, I'd make that a lazy Join struct range: an input range that delivers R1 elements one by one, interspersed with R2 elements. Hmm, now that I think a bit more, I was taking them both (or at least R1) to be ranges of ranges: join(["the","quick","red","fox"], " "). Man, it's 4 pm now, I'll stop.
