I often tried to use bash's for loops to do line by line processing, but it's alway been a pain in the ass. An example. I have a list of files in a text file, and I want to copy each file to some other location. The naïve method:
for F in `cat names.txt`; do cp $F /new/path; done
Unfortunately, names.txt looks like this:
This filename has spaces 1.txt
This filename has spaces 2.txt
...
This filename has spaces N.txt
Bash breaks each line on the space, so the for loop doesn't copy each complete filename. If there are no spaces or tabs in the filenames, then the for loop works ok. The right solution is to use the read command and a while loop:
cat names.txt | while read FILENAME; do cp "$FILENAME" /new/path; done
Update per comment below: added quotes around $FILENAME.
Thanks electricmonk!.