Gnuwin32 find.exe расширяет подстановочный знак перед выполнением поиска
Я использую двоичные файлы Gnuwin32 в среде Windows.
Когда я хочу найти файлы определенного типа, скажем, PDF, я обычно запускаю:
find . -iname '*.pdf' -print
Это прекрасно работает в любой системе UNIX.
find.exe . -iname "*.pdf" -print
Но под Windows, заменив одинарные кавычки на двойные, он работает только тогда, когда в текущем каталоге нет файла pdf, иначе *
расширяется.
Хуже того, когда в текущем каталоге будет ровно один файл PDF, он будет расширяться, синтаксической ошибки не будет, и вы получите неправильные результаты.
Я пытался избежать *
с каретой, обратной косой чертой, самой звездой, вставляя двойные кавычки: у меня ничего не работает.
Реальный пример:
Хорошо, вот все мои файлы:
C:\tmp>find . -type f
./a/1.pdf
./a/2.pdf
./a/aa/1.pdf
./b/1.pdf
./b/bb/1.pdf
./b/bb/2.pdf
Хорошее поведение, шаблон не был расширен
C:\tmp>find . -iname "*.pdf"
./a/1.pdf
./a/2.pdf
./a/aa/1.pdf
./b/1.pdf
./b/bb/1.pdf
./b/bb/2.pdf
C:\tmp>cd a
Осторожно, противоречивое поведение, подстановочный знак был расширен:
C:\tmp\a>find . -iname "*.pdf"
find: paths must precede expression
Usage: find [-H] [-L] [-P] [path...] [expression]
C:tmp\a>cd ..\b
Осторожно, противоречивое поведение, подстановочный знак был расширен:
C:\tmp\b>find . -iname "*.pdf"
./1.pdf
./bb/1.pdf
Спасибо
5 ответов
Я нашел решение моей проблемы.
- gnuwin32-х
find.exe
не работает с последними версиями Windows (Vista, Seven), потому что он расширяет подстановочные знаки, соответствующие только содержимому текущего каталога. - Точно так же старая версия find.exe от UnxUtils страдала той же ошибкой.
- Последний
find.exe
от UnxUtils работает.
Одним из обходных путей является добавление подстановочного знака / расширения, которое оболочка Windows не раскрывает, но GNU find делает так:
find.exe . -name *[.:]pdf -print
Оболочка Windows [*] не интерпретирует / не расширяет квадратные скобки. Кроме того, двоеточие не является допустимым символом в именах файлов Windows, поэтому этот шаблон не может совпадать ни с одним из имен файлов Windows, и оболочка Windows всегда передает шаблон в файл find.exe.
Find.exe найдет все файлы, заканчивающиеся на .pdf
или же :pdf
, но так как никакие файлы не могут иметь имя, заканчивающееся на :pdf
под Windows он найдет только файлы, оканчивающиеся на .pdf
,
[*] Это среда выполнения C, которая не выполняет / не выполняет эти подстановочные знаки. Я недостаточно хорошо понимаю среду выполнения Win32 C, чтобы уточнить это различие, поэтому сейчас для целей этого обходного пути я просто говорю "оболочка".
Я страдал от этой проблемы сегодня днем. UnxUtils Бенуа может работать. Я также считаю, что MinGW find.exe может работать, он находится под моим
"MinGW\ MSYS \1,0\ Bin"
каталог. И это согласуется с руководством.
gnuwin32 и UnxUtils:
find.exe . -name GameCli*
работать, ноfind.exe . -name 'GameCli*'
не работаетMinGW-х
find.exe . -name 'GameCli*'
Работа.
Я не нашел ничего лучше, чем просто избегать подстановочных знаков
find.exe . -iregex ".+\.pdf" -print
@OP, у меня постоянное поведение
C:\test\temp>find . -iname "*.txt"
./1.txt
./2.txt
C:\test\temp>cd a
C:\test\temp\a>find . -iname "*.txt"
C:\test\temp\a>cd ..\b
C:\test\temp\b>find . -iname "*.txt"
C:\test\temp\b>find --version
GNU find version 4.2.20
Features enabled: CACHE_IDS D_TYPE
Вы можете попытаться использовать findutils вместо UnxUtils.