How to Read File Line Using Bash “while” Loop [8 Cases]

Reading a file line by line is a must-have skill that any developer needs to learn to master bash scripting. One of the easiest methods to read file content is the use of a read command in conjunction with a while loop that loops through a file line by line and facilitates data manipulation and processing. The while loop with the read command can be used in various ways for reading file information. In this article, I will walk you through the 8 cases to read a file line with the while loop in Bash. Stay tuned.

8 Cases to Read File Line Using “while” Loop in Bash

A while loop offers versatile features, so it can be used in combination with the read command in 8 ways to read a file line. Here. I will explain how the read, cat, awk, grep, etc. commands are used for reading file content. Additionally, to read file lines using command-line argument, IFS variable, and process substitution will also be addressed.

Download this file.txt to work with the following methods. Here’s the content of the file:

contents of file.txt

1. Using “read” Command Alone

To read a file line in bash, use only the read command within the while loop. The read command can read an entire file line by line through a while loop. Follow the script below to see how the while loop works with the read command for reading file lines:

#!/bin/bash
filename="file.txt"
while read line; do
echo $line
done < "$filename"
EXPLANATION

Here, filename="file.txt" assigns the file.txt to the variable filename. Then the while read line; do starts the while loop and continues to read file line by line and echoes each line (read by the read command) to the terminal with the echo $line. Finally, the done < $filename uses input redirection (<) to redirect the input from the file specified by the “filename” variable.

reading file line with read command using while loop

This picture shows that the script prints each line of file.txt. However, it does not show the backslash sign \ from the file. To preserve the backslashes, use the -r option with the read command. Here’s how:

#!/bin/bash
filename="file.txt"
while read -r line; do
echo $line
done < "$filename"
EXPLANATION

The while read command with the -r option reads the file line from “file.txt” including backslashes and prints the line that is read by the read command in the terminal using the echo command.

reading file line including backslashes with read command using while loop

Now, you can see that the file is read including backslashes by the read command in a while loop.

2. Using “cat” Command

In this example, the cat command is piped with the while read -r line to read line from the file.txt. The piping operator | is used to take the output of the cat command as input of the while loop. Copy the script to read a file line using the cat command:

#!/bin/bash
filename="file.txt"
cat "$filename" | while read -r line
do
echo $line
done
EXPLANATION

The cat command concatenates and displays the content of the specified file. Then the output is piped to the while loop as input. Lastly, the while loop with the read -r command reads each line of the file.txt and prints the read line in the terminal using the echo command.

reading file with cat command using while loop

As you can see, the script reads the file content and prints it in the terminal.

3. Using IFS (Internal Field Separator)

Within a while loop, the IFS (Internal Field Separator) can be incorporated with the read command to read a file line by line. The value of IFS determines which characters are treated as field separators. Now, take a look at the following bash script to use the IFS with a while loop to read file content:

#!/bin/bash
filename="file.txt"
while IFS= read -r line
do
echo $line
done < "$filename"
EXPLANATION

while IFS= read -r line reads line by line from the file.txt. Here, the IFS sets to nothing to preserve the leading and trailing whitespaces. After that, the echo command prints each read line by the while loop.

reading file using IFS

You can see in the image that all the lines of the “file.txt” are printed on the terminal.

4. Using Command-line Argument

In this example, to read the file content, the filename will be taken as a command-line argument. Here, the $1 is a positional parameter indicating the first argument passed to the script. To know how to use it for reading file lines, check the script below:

#!/bin/bash
filename=$1
while read -r line; do
echo $line
done < $filename
EXPLANATION

Before starting the while loop, the $1 passed the file.txt from the command line to the variable filename. Then the while read -r line continues to read the file content including the backslash character due to the -r option with the read command. After reading the entire file, the script outputs the content to the console by the echo command.

Run the script with this command to get the following output:

./argument.sh file.txt

reading file line using command-line argument with while loop

As you can see, every line of the file.txt is shown on the terminal.

5. Using “awk” Command

A powerful text-processing tool in Linux and other Unix-like operating systems is the awk command. In order to read the file line by line, the while loop is piped with the awk command here:

#!/bin/bash
filename="file.txt"
awk '{print}' "$filename" | while read -r line
do
echo $line
done
EXPLANATION

The script uses the awk command to print each line of the file.txt specified by the variable filename. Then the output of this command is passed to the while loop as input through the pipe operator. while read -r line reads file lines from the standard input (the output of the awk command) and prints them in the terminal using echo $line.

reading file using awk command

The image illustrates each line of the “file.txt” read by the while loop.

6. Using here String

The here string in bash passes a string as the input to a command using the <<< operator. This example shows how to use this here string operator to read a file line by line. To achieve this, copy the script:

#!/bin/bash
filename="file.txt"
while read -r line
do
echo "$line"
done <<< "$(cat "$filename")"
EXPLANATION

After assigning the file.txt to the variable filename, while read -r line continues to read the file line one by one. The echo command displays each line to the console. done <<< "$(cat "$filename")" uses here string operator <<< to provide the file content as input to the while loop. The cat $filename reads the contents of the file and the output is captured by the command substitution “$(…)”.

reading file line using here string in a while loop

Upon script execution, the file contents are shown in the output.

7. Using File Descriptor

This example shows how to use a file descriptor within a while loop to read a file line. The file descriptor in Bash is a non-negative unique identifier for an open file or input/output stream. It represents what is connected to the shell script whether it is a file, network connection, or terminal.

The reserved file descriptors are as follows:

  • File Descriptor 0 (standard input): The stream from which a command reads its input data. It is connected to the keyboard by default.
  • File Descriptor 1 (standard output): The stream to which a command writes its output data. It is connected to the terminal by default.
  • File Descriptor 2 (standard error): The stream from which a command writes its error messages. It is connected to the terminal by default.

The file descriptors beyond 2 are used to represent other streams like an open file or network connections.

In the following script, the file descriptor 3 is used for the file named “file.txt” to read the contents of the file:

#!/bin/bash
while IFS= read -r -u3 line; do
echo "$line"
done 3< file.txt
EXPLANATION

The script initiates a while loop that reads each line from the file descriptor 3 (u3) and stores it in the variable line. The IFS is set to empty string to avoid unintended word spitting and the -r option preserves the backslash characters. echo "$line" prints the current read line of the file. done 3< file.txt redirects the “file.txt” to the file descriptor 3 which means the read command will read from this file.

reading file line using file descriptor within a while loop

Every line that was read from the file.txt is shown in the image.

8. Using Process Substitution

Process substitution uses <(...) syntax to create a temporary file from the output of a command that allows direct use as input for other commands. In this example, for reading file lines of the file.txt, process substitution is used. Follow the script to know more about it:

#!/bin/bash
while IFS= read -r line; do
echo "$line"
done < <(cat file.txt)
EXPLANATION

while IFS= read -r line; do starts a while loop that reads each line from the input source preserving the whitespaces and prints the read line in the terminal. done < <(cat file.txt) uses process substitution <(...) that creates a temporary file-like stream from the output of the cat file.txt command and redirects the output to the standard input of the while loop.

reading file line using process substitution

You can see the read line from the “file.txt” file in this picture.

To read a file line, you can also use grep command with the process substitution operator <(...) that takes the output of the grep command as input and redirects it to the while loop. Copy the script below to achieve this task:

#!/bin/bash
filename="file.txt"
while IFS= read -r line
do
echo "$line"
done < <(grep "" "$filename")
EXPLANATION

The while IFS= read -r line initiates a while loop that reads each line from the output of the grep "" "$filename" command and prints the lines in the terminal using the echo command. The grep "" part is used here to read all lines from the file.

reading file using grep command

The image shows all the lines of the “file.txt” read by the grep command.

How to Read File Line in Reverse Order?

Using a while loop with the tac command, a file line can be read in reverse order. The tac command concatenates and displays the contents of the file reversely. The while loop is combined with a for loop to read the file backward while printing the results in the original sequence. Look at the script for better understanding:

#!/bin/bash
filename="file.txt"
lines=()
while IFS= read -r line
do
lines+=("$line")
done < <(tac "$filename")

for ((n=${#lines[@]}-1; n>=0; n--))
do
echo "${lines[$n]}"
done
EXPLANATION

The script starts by assigning “file.txt” to a variable filename. lines=() initializes an array to store the lines read from the file.txt. while IFS= read -r line starts a while loop that reads the line from the output of the tac "$filename" (reverses the lines of the file). lines+=("$line") appends each line to the lines array.

done < <(tac "$filename") uses process substitution <(...) to treat the output of tac "$filename" as a file and then redirects that output to the standard input of the while loop.

After that, a for loop is initialized to iterate through the lines array in reverse order. Finally, echo "${lines[$n]}" prints each line to the terminal in its original order.

reading file in reverse order

You can see all the lines from the file.txt in the original order but it is read in the reverse order.

Common Issues in Bash File Reading With “while” Loop

When reading a file line by line, you can come across certain common issues, such as handling special characters or empty lines. The solutions to these issues are covered in this section.

Dealing With Empty Lines

A file can contain empty lines and the read command within a while loop by default can read a file including those empty lines. If you want to skip the empty lines from being read, you can follow the script below:

#!/bin/bash
filename="file.txt"
while IFS= read -r line; do

# Skip empty lines
if [[ -n "$line" ]]; then

# Process non-empty lines
echo "$line"
fi
done < "$filename"

This script will only show the lines with content skipping the empty lines:

skipping empty lines during reading a file using while loop

Managing Special Characters

By default, the read command within a while loop can not read backslash character \. So to preserve the backslashes, you can use the -r option with the read command inside the while loop. Check method 1 for the bash script to manage special characters like \.

Practice Tasks on How to Read File Line Using Bash “while” Loop

Do the following tasks to sharpen your understanding of how to read a file line using a while loop:

  1. Make a bash script that displays each read line of the “file.txt” along with its line numbers.
  2. Write a bash script that reads the “file.txt” and prints only the non-empty lines.
  3. Create a file that contains the names of 7 days of the week. Now, read the names of the file using a while loop.
  4. Generate a bash script that prints only the file line containing a specific keyword.
  5. Take a file of your choice, count the number of lines present in that file, and print it in the terminal using bash while loop.

Conclusion

To sum up, I have finished discussing the 8 cases for using a while loop to read a file line by line. Each technique is explained in detail in the demonstration above. I hope this has improved your understanding of using a while loop in various ways to read file data. Have a great day!

People Also Ask

How to skip empty lines or lines starting with specific characters?

You can use an if conditional statement inside the while loop to skip empty lines or lines starting with specific characters. Here’s an example bash script for this:

while read line; do
if [[ -n "$line" && ! "$line" =~ ^@ ]]; then
# process non-empty lines not starting with @
fi
done < file.txt

While reading file lines, this script skips the empty lines and lines containing the specific character “@” of the “file.txt”.

How does the while loop read a file line by line in Bash?

The while loop reads a file line by line in Bash using the read command. Check out the basic syntax for this task:

while IFS= read -r line; do
# Process the current line here
done < "filename"

This script reads a file preserving leading and trailing whitespaces and backslash characters.

How to exit the loop early based on a condition?

To break a while loop early based on a condition, you can use a break statement inside the condition. Here’s an example bash script for this:

while read line; do
if [[ "$line" == "STOP" ]]; then
break
fi
# process lines
done < file.txt

The script exits the loop when the word “STOP” appears on a line while it is reading the lines from the “file.txt”.

What is read command in Bash?

In Bash, a read command is a powerful tool to read input from a user or a file. It can be used to read a file line by line.

Related Articles


<< Go Back to “while” Loop in Bash | Loops in Bash | Bash Scripting Tutorial

Rate this post
LINUX
FUNDAMENTALS
A Complete Guide for Beginners Enroll Course Now
Mitu Akter Mou

Hello, This is Mitu Akter Mou, currently working as a Linux Content Developer Executive at SOFTEKO for the Linuxsimply project. I hold a bachelor's degree in Biomedical Engineering from Khulna University of Engineering & Technology (KUET). Experiencing new stuff and gathering insights from them seems very happening to me. My goal here is to simplify the life of Linux users by making creative articles, blogs, and video content for all of them. Read Full Bio

1 thought on “How to Read File Line Using Bash “while” Loop [8 Cases]”

  1. Hello,

    Thank you very much for these very clear explanations.

    They saved me from writing a script where the commands/scripts executed inside the loop consumed the standard input (STDIN).

    It helped me understand how to use a file descriptor in a while loop.

    Regards.

    Reply

Leave a Comment