For example, if you have a string array: "a", "b", "c", "d", you may want the output to be:
'a', 'b', 'c' and 'd'
Here is a way to do that using a C# extension method:
Comment welcome. I will update with improvements as suggestions come in:
Extension method:
1 2 3 4 5 6 7 8 9 10 11 12 13 | public static string ToHumanReadableString(this IEnumerable<object> enumerable, string quoteWith = "'", string delimitWith = ", ", string delimitLastWith = " or ") { if (enumerable == null) { return string.Empty; } var list = enumerable.ToList(); return !list.Any() ? string.Empty : list.Count == 1 ? $"{quoteWith}{list.Single()}{quoteWith}" : $"{string.Join(delimitWith ?? string.Empty, list.Take(list.Count - 1).Select(item => $"{quoteWith}{item}{quoteWith}"))}{delimitLastWith}{quoteWith}{list.Last()}{quoteWith}"; } |
XUnit tests:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | [Fact] public void JoinForHumansTest() { Assert.Equal("'a'", new List<string> {"a"}.ToHumanReadableString()); Assert.Equal("''", new string[] { null }.ToHumanReadableString()); Assert.Equal("'a'", new[] { "a" }.ToHumanReadableString()); Assert.Equal("'a' or 'b'", new[] { "a", "b" }.ToHumanReadableString()); Assert.Equal("'a' or ''", new[] { "a", null }.ToHumanReadableString()); Assert.Equal("'a', 'b' or 'c'", new[] {"a", "b", "c"}.ToHumanReadableString()); Assert.Equal("'a', 'b', 'c' or 'd'", new[] {"a", "b", "c", "d"}.ToHumanReadableString()); Assert.Equal("'a';'b';'c' or 'd'", new[] {"a", "b", "c", "d"}.ToHumanReadableString(delimitWith: ";")); Assert.Equal("'a', 'b', 'c' and 'd'", new[] {"a", "b", "c", "d"}.ToHumanReadableString(delimitLastWith: " and ")); Assert.Equal("a, b, c or d", new[] {"a", "b", "c", "d"}.ToHumanReadableString(string.Empty)); Assert.Equal("abcd", new[] {"a", "b", "c", "d"}.ToHumanReadableString(null, null, null)); Assert.Equal("", ((string[]) null).ToHumanReadableString(null, null, null)); } |