Assuming that your file names contain no spaces or quotes:
ls dir_name \
| xargs -L 2 \
| while read FILE1 FILE2; do \
printf "file1 %s file2 %s\n" "$FILE1" "$FILE2"
done
Example:
$ ls
a b c d e f
$ ls . \
| xargs -L 2 \
| while read FILE1 FILE2; do \
printf "file1 %s file2 %s\n" "$FILE1" "$FILE2"
done
file1 a file2 b
file1 c file2 d
file1 e file2 f
Note 1:
Because of the pipes, each execution of printf is in another shell process. Setting variables won't apply across loop iterations. If you want to do that, you can read all the lines into an array with
readarray -t FILES < <(ls dir_name | xargs -L 2)
and then iterate the array with
COUNT=0
for LINE in "${FILES[@]}"; do
FILE1="${LINE%% *}"
FILE2="${LINE##* }"
printf "file1 %s file2 %s\n" "$FILE1" "$FILE2"
((COUNT++))
done
This allows you to set variables e.g. COUNT across iterations, however, it takes more memory and stops working when you want the files in triplets.
You can use an array for an arbitrary tuple of files:
COUNT=0
for LINE in "${FILES[@]}"; do
TUPLE=( $LINE ) # note: no quotes
printf "file1 %s file2 %s\n" "${TUPLE[0]}" "${TUPLE[1]}"
((COUNT++))
done
Note 2:
You can also use readarray's callback mechanism:
COUNT=0
callback()
{
TUPLE=( $2 ) # note: no quotes
printf "file1 %s file2 %s\n" "${TUPLE[0]}" "${TUPLE[1]}"
((COUNT++))
}
...
readarray -t -C callback -c 1 FILES < <(ls dir_name | xargs -L 2)