Ryan Williams
Ryan Williams

Reputation: 173

Perl regexs: replace a run of spaces and newlines

File bar's whitespace consists only of spaces and newlines:

$ cat bar
1, 2,
  3,
4

I want to replace consecutive runs of whitespace (spaces and newlines) with S, i.e. desired output is:

1,S2,S3,S4S

However, all my attempts result in \n being replaced by one S, and spaces that immediately follow it replaced by another S:

$ cat bar | perl -pe 's/\s+/S/g'
1,S2,SS3,S4S
$ cat bar | perl -pe 's/\s+/S/gm'
1,S2,SS3,S4S
$ cat bar | perl -pe 's/\s+/S/gms'
1,S2,SS3,S4S
$ cat bar | perl -pe 's/[ \n]+/S/gms'
1,S2,SS3,S4S
$ cat bar | perl -pe 's/[ \n]+/S/gm'
1,S2,SS3,S4S
$ cat bar | perl -pe 's/[ \n]+/S/g'
1,S2,SS3,S4S

These are all the combinations of relevant regex flags I can think of: /g (global substitution), /s (let . match newlines), and /m (multi-line); I always have SS preceding the 3, where I want just S.

Any help would be much appreciated!

Upvotes: 1

Views: 99

Answers (1)

choroba
choroba

Reputation: 241768

perl -p reads the input line by line. You need to read the whole input at once, or remember whether the previous line ended in whitespace.

perl -0777 -pe 's/\s+/S/g'

-0777 reads the whole file at once.

perl -pe 's/^\s+// unless 1 == $.; s/\s+/S/g;'

Here, any leading whitespace is removed (except for the first line). We know it must be preceded by a newline, anyway.

Upvotes: 3

Related Questions