greg0ire
greg0ire

Reputation: 23255

preserve whitespace while iterating over a file in bash

I need to iterate over the lines of a text file in bash, and I want to preserve whitespace. The final goal is to feed this line phrases that could contain a whitespace.

So, given a phrase_file containing

xdebug
var_dump
 dump(
pwet
meuh
coin

when I try this :

while read -r PHRASE
do
    echo "$PHRASE"
done < phrase_file

The output is :

xdebug
var_dump
dump(
pwet
meuh
coin

Where did the whitespace before dump() go , and how can I get it back?

Upvotes: 2

Views: 1765

Answers (3)

chepner
chepner

Reputation: 531798

-r treats the input literally, but supplying an argument to read causes the line to be split according to IFS, a side-effect of which with the default value is to remove leading and trailing whitespace. As Tom Fenech pointed out, bash read can omit an argument, with the unsplit output stored in REPLY. If you don't want to use REPLY, you can simply set IFS to a null string to prevent word-splitting.

# all uppercase variable names are reserved for the shell;
# put at least one lowercase letter or number in your names
while IFS= read -r phrase; do
    echo "$phrase"
done < phrase_file 

Upvotes: 2

fedorqui
fedorqui

Reputation: 290025

Just set the IFS variable to empty:

while IFS= read -r var;
do
   echo "$var"
done < file

Which returns:

$ while IFS= read -r var; do echo "$var"; done < file
xdebug
var_dump
 dump(
pwet
meuh
coin

From How can I read a file (data stream, variable) line-by-line (and/or field-by-field)?:

IFS= prevents trimming of leading and trailing whitespace.

Upvotes: 3

Tom Fenech
Tom Fenech

Reputation: 74685

You can use the built-in $REPLY variable, which captures the entire line:

while read -r; do
    echo "$REPLY"
done < phrase_file

Note that if you name a variable (like PHRASE in your example), then $REPLY is not set.

Upvotes: 7

Related Questions