In bash, I know that it is possible to write a for loop in which some loop control variable i iterates over specified integers. For example, I can write a bash shell script that prints the integers between 1 and 10:
#!/bin/bash
for i in {1..10}
do
echo $i
done
Is it possible to instead iterate over a loop control variable that is a string, if I provide a list of strings? For example, suppose that I have a string fname that represents a file name. I want to call a set of commands for each file name. For example, I might want to print the contents of fname using a command like this:
#!/bin/bash
for fname in {"a.txt", "b.txt", "c.txt"}
do
echo $fname
done
In other words, on the first iteration, fname should have the value fname="a.txt", while on the second iteration, fname should have the value fname="b.txt", and so on. Unfortunately, it seems that the above syntax is not quite correct. I would like to obtain the output:
a.txt
b.txt
c.txt
but when I try the above code, I obtain this output:
{a.txt,
b.txt,
c.txt}
Can you please help me determine the correct syntax, so that I can iteratively change the value/contents of the variable fname? Thank you for your time.
Answers:
Thank you for visiting the Q&A section on Magenaut. Please note that all the answers may not help you solve the issue immediately. So please treat them as advisements. If you found the post helpful (or not), leave a comment & I’ll get back to you as soon as possible.
Method 1
The correct syntax is as follows:
#!/bin/bash for fname in a.txt b.txt c.txt do echo $fname done
Method 2
Seems to me you should just do…
printf %s.txt\n a b c
Method 3
As noted by user13742 in the comments, we can make use of arrays in bash and ksh:
#!/usr/bin/env bash
files_list=( "a.txt" "b.txt" "c and space.txt" )
for i in "${files_list[@]}"
do
echo "$i"
# do something else here,maybe
done
And works as so:
$ ./iterate_files_array.sh a.txt b.txt c and space.txt
However, some shells such as dash ( /bin/sh on Ubuntu ) don’t support arrays. In such case we could resort to using here-document structure: <<
#!/bin/sh
while IFS= read -r line
do
echo "$line"
done << EOL
one.txt
two.txt
with space.txt
EOL
All methods was sourced from stackoverflow.com or stackexchange.com, is licensed under cc by-sa 2.5, cc by-sa 3.0 and cc by-sa 4.0