Как рекурсивно искать каталоги в минимальной оболочке (без grep, find и т. Д.)? - PullRequest
4 голосов
/ 04 ноября 2011

Я работаю со встроенной системой, работающей под управлением QNX, с урезанной оболочкой (KSH).

Я хочу найти все запускаемые все исполняемые файлы в файловой системе, которые соответствуют следующему:

*/shle/*-*_test

Каталог "shle" может отображаться на глубине до 4 уровней в корневом каталоге.Мой текущий подход заключается в запуске следующих команд:

for shle in ./shle ./*/shle ./*/*/shle ./*/*/*/shle
do
  for exe in $shle/*-*_test
  do
    echo running: $exe
    $exe
  done
done

Есть ли более чистый или быстрый способ сделать это?Есть ли другие команды, кроме grep и find, которые я должен попробовать?

Ответы [ 2 ]

3 голосов
/ 04 ноября 2011

Вы можете попробовать использовать опцию globstar и указать ** / shle, чтобы найти каталоги с одним или несколькими уровнями глубины.

На странице ksh:

          ∗      Matches any string, including the null string.  When used
                 for filename expansion, if the globstar option is on, two
                 adjacent  ∗'s  by itself will match all files and zero or
                 more directories and subdirectories.  If followed by a  /
                 then only directories and subdirectories will match.
2 голосов
/ 05 ноября 2011

Если у вас нет find, вы не можете сделать намного лучше, чем то, что вы сделали: перечислите уровни. Если вам нужно перейти на произвольные уровни, вы можете сделать это с помощью рекурсивной функции (но будьте осторожны, рекурсия сложна, когда у вас есть только глобальные переменные). К счастью, с известной максимальной глубиной это намного проще.

Есть немного возможностей для улучшения: вам лучше поставить двойные кавычки вокруг всех подстановок переменных, если где-то есть имя файла, которое содержит пробел или специальные символы. И вы не проверяете, существует ли $exe и является ли он исполняемым (это может быть шаблон …/*-*_test, если этот шаблон ничего не соответствует, или, возможно, это неисполняемый файл).

for shle in shle */shle */*/shle */*/*/shle; do
  for exe in "$shle"/*-*_test; do
    test -x "$exe" && "$exe"
  done
done

Если у вас даже нет test (если у вас есть ksh, он встроен, но если это урезанная оболочка, которой он может отсутствовать), вам может понадобиться более сложный тест, чтобы увидеть, шаблон был расширен:

for shle in shle */shle */*/shle */*/*/shle; do
  for exe in "$shle"/*-*_test; do
    case "$exe" in
      */"*-*_test") :;;
      *) "$exe";;
    esac
  done
done

(Я удивлен, что у вас нет find, я думал, что QNX поставляется с полным пакетом POSIX, но я незнаком с экосистемой QNX, это может быть урезанная версия ОС для небольшое устройство.)

...