Solution using gawk
and a recent version of bash
There is a bash
primitive to handle file[038-040].txt
. It makes the code quite simple:
gawk 'FNR==1 {print FILENAME, $0} {quit}' file{038..040}.txt
Key points:
FNR==1 {print FILENAME, $0}
This prints the filename and the first line of each file
{quit}
This saves time by skipping directly to the next file.
file{038..040}.txt
The construct {038..040}
is a bash feature called brace expansion. bash
will replace this with the file names that you want. If you want to test out brace expansion to see how it works, try it on the command line with this simple statement:
echo file{038..040}.txt
UPDATE 1: Mac OSX currently uses bash v3.2 which does not support leading zeros in brace expansion.
UPDATE 2: If there are missing files and you have a modern gawk
(v4.0 or better), use this instead:
gawk 'BEGINFILE{ if (ERRNO) nextfile} FNR==1 {print FILENAME, $0} {quit}' file{038..040}.txt
Solution using gawk
with a plain POSIX shell
gawk '{n=0+substr(FILENAME,5,3)} FNR==1 && n>=38 && n<=40 {print FILENAME, $0} {quit}' file*.txt
Explanation:
n=0+substr(FILENAME,5,3)
Extract the number from the filename. 0+
is a trick to force awk
to treat n
as numeric.
n>=38 && n<=40 {print FILENAME, $0}
This selects the file based on its number and prints the filename and first line.
{quit}
As before, this saves time by stopping awk
from reading the rest of each file.
file*.txt
This can be expanded by any POSIX shell to the list of file names.