2

I came to a section of a bash book that is trying to show me that you can use a read statement in conjunction with a while loop to read each line of a file, and then capture the first two words into two variables. However, I wrote my own script to test it below.

$ cat hoststest 
192.168.1.1 pc1 word3 word4
192.168.1.2 pc2 word3 word4
$ cat t13
#!/bin/bash
while read ip_address pc_number restofstuff
do
if [ ! -z "$ip_address" ]; then
    echo "IP is $ip_address and its for $pc_number"
fi
done < "/home/john/hoststest"
$ ./t13
IP is 192.168.1.1 and its for pc1
IP is 192.168.1.2 and its for pc2

In my original test I did not have the third variable "restofstuff". What happened was that instead of the pc_number variable getting just either pc1 or pc2 as it's value, pc_number was being stored as the rest of the line. So I added this third variable to just not get all the rest of the line as part of the pc_number. What I've done works now, with this "restofstuff" variable, but it doesn't feel like I'm doing this right. I've just basically made a "dead" variable that does nothing. If I was trying to carry on with using the read + while loop, what would be the right way to go about it (note, it's the while loop + read combination I'm working with/learning, so I want to stay focused on that).

  • 2
    Nope, you're doing it the correct way, if you want to do it with read. You can use awk or cut to only print the fields you need, and then you won't need the "rest" variable. But in general that's the way to go. – aviro Dec 14 '22 at 18:10
  • In fact, it is valid to discard any fields, not just the excess ones at the end, and to put all the unwanted data into the same variable. If you only want the third and fifth fields, this works: read -r X X third X fifth X. – Paul_Pedant Dec 15 '22 at 09:40

1 Answers1

8

That’s just how read works: if there are more fields in its input than variables, the last variable is assigned the corresponding field and all the left-overs. Typical practice is to name this variable _:

while read ip_address pc_number _

See Understanding "IFS= read -r line" for an in-depth discussion of read, and Why is using a shell loop to process text considered bad practice?

Stephen Kitt
  • 434,908