53

Normally you would write:

diff file1 file2

But I would like to diff a file and output from the command (here I make command a trivial one):

diff file1 <(cat file2 | sort)

Ok, this work when I enter this manually at shell prompt, but when I put exactly the same line in shell script, and then run the script, I get error.

So, the question is -- how to do this correctly?

Of course I would like avoid writing the output to a temporary file.

greenoldman
  • 6,176

2 Answers2

61

I suspect your script and your shell are different. Perhaps you have #!/bin/sh at the top of your script as the interpreter but you are using bash as your personal shell. You can find out what shell you run in a terminal by running echo $SHELL.

An easier way to do this which should work across most shells would be to use a pipe redirect instead of the file read operator you give. The symbol '-' is a standard nomenclature for reading STDIN and can frequently be used as a replacement for a file name in an argument list:

cat file2 | sort | diff file1 -

Or to avoid a useless use of cat:

sort < file2 | diff file1 -
Caleb
  • 70,105
  • Ah, you are good, indeed, I didn't check if sh is bash or not. Thank you very much for the solution. – greenoldman Apr 21 '11 at 10:04
  • It is diffing file with stdout. Now how to diff stdout with a file? I mean, the opposite direction. it's -R in case of using git diff --no-index – Nakilon Jan 04 '18 at 21:49
  • @Nakilon You would just change the argument order: diff - file1. – Caleb Jan 05 '18 at 06:53
  • Cool. This didn't work for git diff. – Nakilon Jan 06 '18 at 04:49
  • @Nakilon Of course not, why would it? git diff is a completely different beast and operates on references to glob objects in its internal index, not files; diff operates on the file system. The - syntax is just shell syntactic sugar for /dev/stdin, the file representing the STDIN stream. Hence why diff can use it as a substitute for a file name. Meanwhile git diff isn't looking for files, it's looking up objects so you have to pass it something it recognizes. Don't use it to compare files to each other, use diff for that. – Caleb Jan 09 '18 at 12:45
-3

The scope of the standard input it's the script itself, so just put your code inside a blocku like this:

{
  diff file1 <(sort file2)
}

In this way the scope of the STDIN it's inside the block..

I've tried and it works.

tmow
  • 1,255