9

I use ubuntu 14.4, and attempt to redirect the output of grep command to a file, but I keep getting this error:

grep: input file 'X' is also the output

I've searched for this issue and just found out that it was a bug in ubuntu 12.4 and there is not any describe about, can anybody help me to figure out this problem?

I run the following command:

grep -E -r -o -n r"%}(.*){%" > myfile
  • If you are trying grep pattern file > file then it doesn't work. You cannot use the same file as input and output for grep. – jimmij Oct 25 '14 at 21:29
  • i add my command ! thanks for hint , but when i try to use a file in other path the does not predicate it and i cant do that ! – Kasrâmvd Oct 25 '14 at 21:34
  • for example with ../f i get this bash: ../f.txt: Permission denied – Kasrâmvd Oct 25 '14 at 21:37
  • show full command, what is your input file, or are you using the pipe? – jimmij Oct 25 '14 at 21:42
  • 1
    Now I understand that you are actually greping recursively the whole directory structure and want to append the result to the file which already exists in this structure. The problem is that shell (bash, zsh, whatever) first performs redirections and only then goes back to commands (grep in this example). It means that grep in command grep pattern file > file sees already empty file, so has nothing as input. However if you use >> instead of > then the file is not empty, but grep throws error anyhow as it may lead to recursive processing the same line (pattern) over and over again. – jimmij Oct 25 '14 at 22:22
7

It is not possible to use the same file as input and output for grep. You may consider the following alternatives:

  • temporary file

    grep pattern file > tmp_file
    mv tmp_file file
    
  • sed

    sed -i -n '/pattern/p' file
    
  • put whole file in the variable (not bright idea for large files)

    x=$(cat file); echo "$x" | grep pattern > file
    
  • sed can be more portable sed -i '/pattern/!d' file – Costas Oct 25 '14 at 21:53
  • But in the case OP wants sed -i -n 's/.*\(pattern\).*/\1/p' file – Costas Oct 25 '14 at 22:20
  • @Costas you are right, the question was edited and additional info added so one can polish sed syntax as well. – jimmij Oct 25 '14 at 22:35
4

You can use the --exclude field in your grep command like so:

grep  --exclude=myfile  -Eron  r"%}(.*){%"  >  myfile
  • 2
    Make sure myfile is unique as it only applies to the file's basename. You don't want to skip files with the same name in other directories. – Walf Mar 7 '17 at 0:45
1

I found a way in bash: cat >> IN_OUTPUT_FILE <<< "$(grep something IN_OUTPUT_FILE)"

The command in <<<"..." will be executed first.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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