grep: вхідний файл "X" - це також вихід


12

Я використовую ubuntu 14.4та намагаюся перенаправляти вихід grepкоманди в файл, але я продовжую отримувати цю помилку:

grep: input file 'X' is also the output

Я шукав цю проблему і тільки що дізнався, що це помилка, ubuntu 12.4і немає жодного опису, чи може хтось допомогти мені розібратися в цій проблемі?

Я запускаю таку команду:

grep -E -r -o -n r"%}(.*){%" > myfile

Якщо ви намагаєтесь, grep pattern file > fileце не працює. Ви не можете використовувати той самий файл, що і для введення та виводу для grep.
jimmij

я додаю свою команду! дякую за підказку, але коли я намагаюся використовувати файл в іншому шляху, це не передбачає, і я не можу це зробити!
Касрамвд

наприклад з ../fi отримати цеbash: ../f.txt: Permission denied
Kasramvd

показати повну команду, який ваш вхідний файл, або ви використовуєте трубу?
jimmij

1
Тепер я розумію, що ви насправді репресивно зіставляєте всю структуру каталогів і хочете додати результат до файлу, який вже існує в цій структурі. Проблема полягає в тому, що оболонка (bash, zsh, що завгодно) спочатку виконує перенаправлення і лише потім повертається до команд (grep в цьому прикладі). Це означає, що grepкоманда grep pattern file > fileбачить вже порожній файл, тому не має нічого як вхідний файл. Однак якщо ви використовуєте >>замість >цього, файл не порожній, але grep видає помилку так чи інакше, оскільки це може призвести до рекурсивної обробки однієї і тієї ж лінії (шаблону) знову і знову.
jimmij

Відповіді:


9

Неможливо використовувати той самий файл, що і для введення та виводу grep. Ви можете розглянути наступні альтернативи:

  • тимчасовий файл

    grep pattern file > tmp_file
    mv tmp_file file
  • sed

    sed -i -n '/pattern/p' file
  • помістити весь файл у змінну (не яскрава ідея для великих файлів)

    x=$(cat file); echo "$x" | grep pattern > file

1
sed може бути більш портативнимsed -i '/pattern/!d' file
Costas

Але у випадку, якщо ОП хочеsed -i -n 's/.*\(pattern\).*/\1/p' file
Костас

@Costas ви праві, питання було відредаговано та додано додаткову інформацію, щоб можна було також полірувати sedсинтаксис.
jimmij

5

Ви можете використовувати --excludeполе у ​​вашій grepкоманді так:

grep  --exclude=myfile  -Eron  r"%}(.*){%"  >  myfile

2
Переконайтеся, що myfileвін унікальний, оскільки він стосується лише базового імені файлу. Ви не хочете пропускати файли з тим самим іменем в інших каталогах.
Вальф

1

Я знайшов спосіб у баші: cat >> IN_OUTPUT_FILE <<< "$(grep something IN_OUTPUT_FILE)"

Команда в <<<"..."буде виконана першою.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.