Is there a way to join the elements in an js array, but let the last separator be different?
What I want is something like Array.join(separator)
, but which takes a second argument Array.join(separator, beforeLastElement)
, so when I say [foo, bar, baz].join(", ", " or")
I would get "foo, bar or baz"
. I guess I could write a function that used Array.slice
to separate out the last element, but is there some well known method that I could use instead?
There's no predefined function, because it's quite simple.
var a = ['a', 'b', 'c'];
var str = a.slice(0, -1).join(',')+' or '+a.slice(-1);
There's also a specification problem for the main use case of such a function which is natural language formatting. For example if we were to use the Oxford comma logic we would have a different result than what you're looking for:
// make a list in the Oxford comma style (eg "a, b, c, and d")
// Examples with conjunction "and":
// ["a"] -> "a"
// ["a", "b"] -> "a and b"
// ["a", "b", "c"] -> "a, b, and c"
exports.oxford = function(arr, conjunction, ifempty){
let l = arr.length;
if (!l) return ifempty;
if (l<2) return arr[0];
if (l<3) return arr.join(` ${conjunction} `);
arr = arr.slice();
arr[l-1] = `${conjunction} ${arr[l-1]}`;
return arr.join(", ");
}
So it seems better to let this problem in userland.
May I suggest:
['tom', 'dick', 'harry'].join(', ').replace(/, ([^,]*)$/, ' and $1')
> "tom, dick and harry"
In-line solution using reduce:
[1, 2, 3, 4, 5].reduce((text, value, i, array) => text + (i < array.length - 1 ? ', ' : ' or ') + value);
=> "1, 2, 3, 4 or 5"