Nice analysis !
Hmm I prefer told like this (parenthesis...)
... only if they're followed by (a whitespace char AND a non-whitespace char) OR (if the end of string is reached)
Ha. As often I was a bit lazy and didn't take care of a possible trailing newline
So there are 2 answers, keeping the lazy "+"
$out = StringRegExpReplace($in, '(?<=\S)(\s+?)(?=\s\S|\z)', "")
$out = StringRegExpReplace($in, '(*CR)(?<=\S)(\s+?)(?=\s\S|$)', "")
But (\s+) is the best one indeed, I forgot the ability of the regex engine to look backwards - so the \s in the lookahead is not matched in the group