Как я могу назначить вывод команды переменной оболочки?

Я хочу присвоить результат выражения переменной и объединить ее со строкой, а затем повторить ее. Вот что у меня есть:

#!/bin/bash cd ~/Desktop; thefile= ls -t -U | grep -m 1 "Screen Shot"; echo "Most recent screenshot is: "$thefile; 

Но это приводит:

 Screen Shot 2011-07-03 at 1.55.43 PM.png Most recent screenshot is: 

Таким образом, похоже, что он не получает привязанный к $thefile и печатается по мере его выполнения.

2 Solutions collect form web for “Как я могу назначить вывод команды переменной оболочки?”

Назначение оболочки – это одно слово, без пробела после знака равенства. Так что вы написали присваиваете пустое значение thefile ; кроме того, поскольку назначение сгруппировано с помощью команды, оно делает thefile переменной среды, а назначение является локальным для этой конкретной команды, то есть только вызов ls видит назначенное значение.

Вы хотите захватить вывод команды, поэтому вам нужно использовать подстановку команд :

 thefile=$(ls -t -U | grep -m 1 "Screen Shot") 

(В какой-то литературе показан альтернативный синтаксис thefile=`ls …` ; синтаксис backquote эквивалентен синтаксису в скобках в долларах, за исключением того, что цитирование внутри backquotes странно иногда, поэтому просто используйте $(…) .)

Другие замечания о вашем скрипте:

  • Объединение -t (сортировка по времени) с -U (не сортировка) не имеет смысла; просто используйте -t .
  • Вместо использования grep для сопоставления скриншотов, яснее передать подстановочный знак ls и использовать head для захвата первого файла:

     thefile=$(ls -t *"Screen Shot"* | head -n 1) 
  • Как правило, это плохая идея для анализа вывода ls . Это может сильно потерпеть неудачу, если у вас есть имена файлов с непечатаемыми символами. Однако сортировка файлов по дате затруднительна без ls , так что это приемлемое решение, если вы знаете, что в именах файлов не будут отображаться непечатаемые символы или обратные косые черты.

  • Всегда используйте двойные кавычки вокруг переменных подстановок , т. Е. Здесь пишут

     echo "Most recent screenshot is: $thefile" 

    Без двойных кавычек значение переменной перераспределяется, что может вызвать проблемы, если оно содержит пробелы или другие специальные символы.

  • Вам не нужны точки с запятой в конце строки. Они избыточны, но безвредны.
  • В сценарии оболочки часто бывает полезно включить set -e . Это говорит, что оболочка должна выйти, если какая-либо команда завершилась неудачей (возвращая ненулевой статус).

Если у вас есть поиск GNU (в частности, если вы используете не встроенный Linux или Cygwin), есть другой подход к поиску последнего файла: find список файлов и их даты и используйте sort и tail для извлечения самого младшего файла ,

 thefile=$(find -maxdepth 1 -type f -name "*Screen Shot*" -printf "%T@ %p" | sort -k 1n | tail -n 1) 

Если вы захотите написать этот скрипт в zsh вместо bash, есть намного более простой способ поймать самый новый файл, потому что zsh имеет glob-квалификаторы, которые позволяют подстановочные соответствия не только по именам, но и по метаданным файлов. Часть (om[1]) после шаблона является классификатором glob; om сортирует совпадения по возрастанию (т. е. по времени модификации, новее сначала) и [1] извлекает только первое совпадение. Весь матч должен быть в круглых скобках, потому что это технически массив, так как globbing возвращает список файлов, даже если [1] означает, что в этом конкретном случае список содержит (не более) один файл.

 #!/bin/zsh set -e cd ~/Desktop thefile=(*"Screen Shot"*(om[1])) echo "Most recent screenshot is: $thefile" 

Если вы хотите сделать это с помощью multiline / multiple command / s, вы можете сделать это:

 output=$( bash <<EOF #multiline/multiple command/s EOF ) 

Или:

 output=$( #multiline/multiple command/s ) 

Пример:

 #!/bin/bash output="$( bash <<EOF echo first echo second echo third EOF )" echo "$output" 

Вывод:

 first second third 
  • Опция -F для ls
  • BASH: цикл через ls
  • ls: Нет такой ошибки файла или каталога
  • Сортировка вывода ls, где файлы заканчиваются цифрами
  • Что касается идентичных копий файлов gedit
  • Где MacOS Finder хранит эту информацию (происхождение файла, который был отправлен мне)?
  • Как я могу сначала показать «ls» dotfiles, оставаясь без учета регистра?
  • ls'ing через полное дерево каталогов для создания одного доступного списка файлов
  • Найти список каталогов на один уровень в глубину от соответствующего каталога
  • Список всех файлов под разными папками с одинаковым именем
  • Изменение способа отображения папок в терминале
  • Linux и Unix - лучшая ОС в мире.