I'm attempting to run multiple commands on the same line for multiple files. I have little experience with Linux and I've run into an issue with this command:

tail -n +3 "/usr/local/tmp/csce215/election2008/"*/*.csv | head -n -1 > polls.csv

I'm attempting to get the "middle section" of each file by using tail and head in succession. Unfortunately, tail runs for each file correctly, but head only seems to run for the very last file. Is this possible to do in one command, or is there a better method for doing this? I'd preferably like to use head and tail.

marked as duplicate by G-Man, countermode, user34720, Toby Speight, Wouter Verhelst Jan 18 '17 at 15:42

This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.

  • 1
    In this particular case, assuming you have GNU sed supporting the -s (or --separate) command-line switch, you could do sed -s '3,$!d; $d' file{1..3} path/to/*/*.csv > polls.csv I think – steeldriver Jan 18 '17 at 3:25

The problem is that tail is creating a single stream of data to pass to head, and that is what's been used there.

Instead, you need to process each file - tail to head - and use that result in the polls.csv file.

A one-liner would look like this:

shopt -s nullglob; for name in "/usr/local/tmp/csce215/election2008/"*/*.csv; do echo "==> $name" >> polls.csv; tail -n +3 "$name" | head -n -1 >>polls.csv; echo "" >> polls.csv; done;

The shopt -s nullglob prevents unwanted actions if there are no *.csv files to find.

Of course, since this uses append to file for the redirect, you'll need to delete the polls file after each use, or it will keep growing. Or, modify the commands to clobber it in the beginning:

echo "" > polls.csv; shopt -s nullglob; for name in "/usr/local/tmp/csce215/election2008/"*/*.csv; do echo "==> $name" >> polls.csv; tail -n +3 "$name" | head -n -1 >>polls.csv; echo "" >> polls.csv; done;

With screen limitations it's not shown as one line but type it as one line anyway. Copy/Paste should keep it as one line for you.

Not the answer you're looking for? Browse other questions tagged or ask your own question.