С достаточно недавними Awk и GNU find
вы можете сделать
awk 'FNR==2 { if ($0 ~ /^#/) printf "%s\0", FILENAME; nextfile }' [0-9][0-9]/[0-9]/*.ini |
xargs -r0 echo rm
nextfile
оператор является расширением POSIX, но может отсутствовать в очень старых реализациях Awk,Если ваши файлы маленькие, возможно, просто извлеките nextfile
и согласитесь с незначительной неэффективностью, которую мы читаем до конца каждого файла, даже если нам действительно нужно исследовать вторую строку.
-0
опция xargs
является расширением GNU.Если ваши имена файлов гарантированно не содержат символов новой строки, вы, вероятно, можете обойтись без
awk 'FNR==2 { if ($0 ~ /^#/) print FILENAME; nextfile }' [0-9][0-9]/[0-9]/*.ini |
xargs -r echo rm
Наконец, удалите echo
, чтобы фактически удалить файлы, которые он печатает.
В некоторых другихподробно, Awk обрабатывает каждый входной файл по одной строке за раз и оценивает скрипт для каждого отдельно.Встроенная переменная FNR
устанавливается на текущий номер строки в файле, а FILENAME
- имя текущего файла.Переменная $0
содержит всю строку, и мы проверяем, соответствует ли она регулярному выражению ^#
(начало строки, за которым сразу следует буквальный символ #
);если это так, мы печатаем FILENAME
(в противном случае для этого файла не выводится).Команда nextfile
закрывает текущий файл и сразу переходит к первой строке ввода следующего файла в списке аргументов (или останавливает обработку, если имена файлов не обрабатываются).
Если у вас многоиз подходящих файлов вы не можете использовать подобный шаблон (вы получаете «список аргументов слишком длинный»);если это так, возможно, просто вернитесь к тому циклу, который у вас был.
Непосредственная ошибка в вашей попытке состоит в том, что вам нужны кавычки около #
(в противном случае он помечает оставшуюся часть строки как комментарий);но, конечно, ваш grep
ищет этот символ в любом месте файла, и вы не указали путь к файлу для проверки.С исправленными непосредственными ошибками это будет
# Don't use, still broken
for i in stuff; do
for b in more stuff; do
grep -LZ '#' "$i/$b"/*.ini
done
done |
# or simply grep -LZ '#' [0-9][0-9]/[0-9]/*.ini
xargs -r0 echo rm
, но опять же, вы не можете легко исправить это, чтобы посмотреть только на вторую строку каждого файла.(Обратите также внимание, как я запускаю финал xargs
вне финала done
.)