String hygiene

How about ""[...], or String()[...]?

I started Corner-cases in `Character` classification of whitespace. Could you elaborate there why you don't want "\u{020}\u{301}" to be whitespace?

I think this should clearly be on StringProtocol (and thus String and Substring). If we go with the non-scalar interpretations of whitespace, then we should definitely have it on all 3 (sigh) UnicodeScalarViews in the stdlib.

I think having an overload that takes a Set<Character> would be very useful. The overload that doesn't take such a set could still be implemented more efficiently.

Should we have such trimmed overloads on BidirectionalCollection? Should we have one that takes a Set<Element> and/or one that takes (Element) -> Bool? This could be pretty simple, implemented in terms of drop(while:) from the front and an equivalent (to be pitched, I suppose) drop-while from the back.

This way we can trim e.g. Arrays in general. It would also provide a better interim story for users who are stuck using [UInt8] instead of String.

"start" and "end" already carry connotations, e.g. startIndex and endIndex. Trimming is similar to chaining str.dropFirst(...).dropLast(...), so I suppose "first" and "last" are also up for grabs. Finally, "leading" and "trailing" may also be good names. Directionality doesn't affect sequence order of the graphemes themselves. It applies more so to rendering, presentation, and other interpretation.