То, что вы сделали в обоих ваших примерах, - это поместите >
где текущая оболочка может видеть это, так что перенаправление выполняется только один раз, до того, как команды find и xargs будут выполнены. Это твоя первая проблема.
Ваша вторая проблема заключается в том, что если вы заключите в кавычки >
чтобы он был передан xargs
, он все равно не будет работать, потому что xargs
не передает вашу команду через оболочку, если вы не попросите об этом.
Ваша третья проблема заключается в том, что если вы скажете xargs использовать оболочку для запуска команды, оболочка сделает неправильное действие, если в именах файлов есть забавные символы. (Также xargs делает неправильные вещи с забавными персонажами, но это можно исправить с помощью -0
.)
Другие проблемы, которые могут вас не волновать, включают в себя:
- echo
''
создает не пустой файл, а файл, содержащий новую строку.
- опция
-name
принимает глобальное выражение, а не регулярное выражение.
- Вы можете добавить
-type f
всякий случай, если какие-либо каталоги соответствуют глобусу.
Вот частично исправленная версия команды:
find . -name '*thisisaglob*' -type f -print0 |
xargs -0 -I target sh -c ': > target'
Это решает большинство проблем, которые я упомянул. Тем не менее, остается проблема неправильной интерпретации оболочки имени файла, содержащего метасимволы оболочки. Чтобы это исправить, вам нужно будет указать имя файла для оболочки как параметр, а не как часть команды -c
. Это будет выглядеть так:
find . -name '*thisisaglob*' -type f -print0 |
xargs -0 -I target sh -c ': > "$1"' fnord target
"Фнорд" является заполнителем. Это становится $0
котором мы не нуждаемся.
Теперь, достигнув цели безопасного использования xargs и redirection, я покажу вам, как достичь своей цели, не используя ни один из них.
find . -name '*thisisaglob*' -type f -exec truncate -s 0 '{}' +
Для этого требуется команда truncate
, которая является частью GNU coreutils, а не стандартной утилитой unix, поэтому она менее переносима, но намного проще для чтения, не так ли?