It will be easier to keep to your basic idea, than to do some itterative sed juggling. Maybe a simple for-loop to build the pattern will make it easier to work with.
pat=; for ((i=1; i<=5; i++)) ;do pat="$pat s/ /;/;"; done
sed -e "$pat" myfile
or just dispense with the multiple -e
expression options, and just group them all with the ;
expression seperator.
sed -e "s/ /;/; s/ /;/; s/ /;/; s/ /;/; s/ /;/" myfile
Here is the sed-only version, that you typically probably won't bother with, but which does allow you to specify any number of replacements. (via the {5}
) ...
sed -nre ':check;G;/^.*\nx{5}$/{b print};s/^(.*)\n.*$/\1/;s/ /;/;t inc-tally;:print;P;x;s/.*//;x;b;:inc-tally;x;s/(.*)/\1x/;x;b check' myfile
The above one-liner(?) is a bit scary, so here it is as structured code, to be called via a sed-script file: sed -nrf "$fsed" myfile
:check ## check the tally
G ## pattern+=nl+hold
/^.*\nx{5}$/{ ## we have the full complement of replacements
b print ## branch to print (and continue)
} ##
s/^(.*)\n.*$/\1/ ##
s/ /;/ ## change one space (if one is present)
t inc-tally ## branch_on_substitute
:print ## no more spaces to change
P ## pattern_first_line_print
x;s/.*//;x ## kill the accumulated tally chars in hold
b ## branch to end of proc (continue)
:inc-tally ##
x ## swap_pattern_and_hold
s/(.*)/\1x/ ##
x ## swap_pattern_and_hold
b check ## branch_unconditional