What operating system are you using? I have access to Linux and Solaris systems, but cannot duplicate your problem. I get multiple lines on tty output (to the terminal) but when I run the 'df' in backquotes, all the data is on one line, for each device. This is also true if I pipe 'df' output through 'grep', just as you found.
What I don't understand is why the same doesn't happen for you with the backquotes.
As an untested suggestion, you could do your 'split' into an explicit variable declared outside the loop, and check it's size:
my ($tmp, $prev);
# ...loop here
if (@tmp == 1)
{
@prev = @tmp;
next;
}
You could then merge the two arrays to process with the slice. Perhaps not the most elegant solution, but it has the advantage of not failing if the df output ever changes to be single lines in all cases. Since this is done before creating the hash, it should fix at least that part of the problem.