improving the join function

Daniel Gibson metalcaedes at gmail.com
Mon Oct 11 21:37:12 PDT 2010


Andrei Alexandrescu schrieb:
> I'm looking at http://d.puremagic.com/issues/show_bug.cgi?id=3313 and 
> that got me looking at std.string.join, which currently has the sig:
> 
> string join(in string[] words, string sep);
> 
> A narrow fix:
> 
> Char[] join(Char)(in Char[][] words, in Char[] sep)
> if (isSomeChar!Char);
> 
> I think it's reasonable to assume that people would want to join things 
> that aren't necessarily arrays of characters, so T could be pretty much 
> any type. An obvious step towards generalization is:
> 
> T[] join(T)(in T[][] items, T[] sep);
> 
> But join doesn't really need random access for words - really, an input 
> range should suffice. So a generally useful join, almost worth putting 
> in std.algorithm, would be:
> 
> 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.
> 
> 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.
> 
> I also have a question from people who dislike Phobos. Was there a point 
> in the changes of signature above where you threw your hands thinking, 
> "do the darn string version already and cut all that crap!"?
> 
> 
> Thanks,
> 
> Andrei

Btw: Is "join" not just a (rather trivial) generalization of reduce?

auto inRange = ...; // range of char[]
char[] sep = " ";
auto joined = reduce!( (char[] res, char[] x) {return res~sep~x;}) (inRange);


More information about the Digitalmars-d mailing list