mtveezy
mtveezy

Reputation: 711

sed DON'T remove extra whitespace

It seems everybody else wants to remove any additional whitespace, however I have the opposite problem.

I have a file, call it some_file.txt that looks like

a     b c     d
and    some     more

and I'm reading it line-by-line with sed,

num_lines=$(cat some_file.txt | wc -l)
for i in $(seq 1 $num_lines); do
    echo $(sed "${i}q;d" $file)
    string=$(sed "${i}q;d" $file)
    echo $string
done

I would expect the number of whitespace characters to stay the same, however the output I get is

a b c d
a b c d
and some more
and some more

So it seems that the problem is with sed removing the extra whitespace between chars, anyway to fix this?

Upvotes: 3

Views: 1894

Answers (1)

chw21
chw21

Reputation: 8140

Have a look at this example:

$ echo Hello       World
Hello World
$ echo "Hello       World"
Hello       World

sed is not your problem, your problem is that bash removes the whitespaces when passing the output of sed into echo.

You just need to surround whatever echo is supposed to print with double quotation marks. So instead of

echo $(sed "${i}q;d" $file)
echo $string

You write

echo "$(sed "${i}q;d" $file)"
echo "$string"

The new script should look like this:

#!/usr/bin/env bash
file=some_file.txt
num_lines=$(cat some_file.txt | wc -l)
for i in $(seq 1 $num_lines); do
    echo "$(sed "${i}q;d" $file)"
    string=$(sed "${i}q;d" $file)
    echo "$string"
done

prints the correct output:

a     b c     d
a     b c     d
and    some     more
and    some     more

However, if you just want to go through your file line by line, I strongly recommend something like this:

while IFS= read -r line; do
    echo "$line"
done < some_file.txt

Question from the comments: What to do if you only want 33 lines starting from line x. One possible solution is this:

#!/usr/bin/env bash
declare -i s=$1
declare -i e=${s}+32
sed -n "${s},${e}p" $file | while IFS= read -r line; do
    echo "$line"
done

(Note that I would probably include some validation of $1 in there as well.)

I declare s and e as integer variables, then even bash can do some simple arithmetic on them and calculate the actual last line to print.

Upvotes: 7

Related Questions