Why this sed command prints all the lines?

Why this sed command:
sed /^a/,/i$/p
prints all lines and not just the lines that beginning with "a" and end with "i"?
It is not too clear to me how sed /BEGIN/,/END/p works.

STDIN:

arthuri
John
Johnny
Michael 

STDOUT:

arthuri
arthuri
John
John
Johnny
Johnny
Michael
Michael

Asked By: toddteller

||

sed by defaults prints the pattern space at the end of each cycle as long as the d command has not been invoked.

That can be disabled with the -n option, or by making the first line of the sed script: #n.

So, here, in addition to that default printing, you’re telling sed to also print the pattern space starting with the lines that starts with a and ending with the first line after that that ends with i.

The first line of your input (arthuri) starts with a, but there’s no line after than that ends with i, so the /^a/,/i$/ range is never terminated and all lines are printed (twice because of the default printing at the end).

sed ranges will always include at least 2 lines (except in the special case where the start is on the last line of the input).

To allow the start and end lines to be the same (like arthuri which happens to both start with a and end in i), you can use awk instead:

awk '/^a/, /i$/'

Or perl:

perl -ne 'print if /^a/ .. /i$/'

If you wanted to print the lines that start with a and end in i, you wouldn’t use an address range, but just:

sed '/^a/!d; /i$/!d'

Or:

sed '/^a.*i$/!d'

Or:

sed -n '/^a.*i$/p'

Though here, you might as well use grep:

grep -x 'a.*i'

Note that ^, * and $ are special characters in the syntax of many shells. Generally, you want to quote sed code arguments.

Answered By: Stéphane Chazelas

You can try with below commands too

command1:

awk '/^a.*i$/' filename

command2:

grep "^a.*i$" filename
Answered By: Praveen Kumar BS
Categories: Answers Tags: , ,
Answers are sorted by their score. The answer accepted by the question owner as the best is marked with
at the top-right corner.