Какой лучше: использование; или && для выполнения нескольких команд в одной строке?

В учебных руководствах и практическое руководство я часто вижу объединенные команды. Например,

sudo apt-get update && sudo apt-get install pyrenamer

Кажется, существует четыре возможных коннектора: &, &&, || и ;. Хотя & коннектор ясен мне (он отправляет процесс в фон и оставляет терминал доступным), не ясно, между чем различие && и ;. И я не знал о || до комментария Kaya.

Следующие вопросы имеют дело с различием между этими двумя коннекторами, но делают так главным образом в комментариях:

Таким образом, вот много связанных вопросов:

  1. Между чем различие ; и &&?
  2. Когда необходимо использовать их соответственно? Было бы хорошо видеть некоторые варианты использования: если я хочу выполнить команду, и затем после него завершают работу моего компьютера, какой коннектор я должен выбрать?
  3. Каковы их преимущества и опасности? Robie Basak упоминает в комментарии этому ответу что команда как cd /somewhere_else; rm -Rf * может иметь разрушительные последствия если первый элемент в сбоях цепочки команды, например.
  4. При необходимости, где они происходят из?
553
задан 13 April 2017 в 15:24

6 ответов

Шпаргалка:

A; B    # Run A and then B, regardless of success of A
A && B  # Run B if and only if A succeeded
A || B  # Run B if and only if A failed
A &     # Run A in background.
926
ответ дан 13 April 2017 в 15:24

Использование ; будет выполнять команды независимо от того, успешна первая команда или нет.

Использование && выполнит вторую команду только тогда, когда первая команда будет выполнена успешно (статус 0).

Оба используются с разных точек зрения. Например, для более длительного процесса, скажем, для установки вам необходимо ее скомпилировать и установить. вам следует сделать && make install . Таким образом, установка будет запущена только в случае успешного выполнения make .

Таким образом, для зависимых команд вы должны использовать && .

Wring bash или команды с независимыми командами используйте ; .

Итак, если вы хотите выключить компьютер, даже если первое задание завершилось неудачно, используйте ; , но если хотите, при полном успехе первого задания инициируйте выключение, используйте && .

35
ответ дан 13 April 2017 в 15:24

&& только запускает вторую команду, если первая завершилась со статусом 0 (успешно). ; запускает обе команды, даже если первая завершается с ненулевым статусом.

Ваш пример с && может быть эквивалентно перефразирован как

if sudo apt-get update ; then
    sudo apt-get install pyrenamer
fi
82
ответ дан 13 April 2017 в 15:24

a; b запустит b независимо от статуса выхода a. a && b запустит b только в случае успеха.

Это необходимо и достаточно для ответа на первые 3 вопроса. В частности, 2 слишком широкое значение, и на него нельзя дать «один» окончательный ответ - лучше всего решать в каждом конкретном случае.

Что касается четвертого вопроса: Это синтаксис Bash .

Также нет никакой опасности в использовании. Опять же, приведенного выше определения достаточно. Это означает, что вы напишете && , когда b окажет непреднамеренное воздействие, если a не удастся. ИМХО, нет необходимости в дополнительных правилах или пояснениях.

16
ответ дан 13 April 2017 в 15:24

A; B # Выполните A, а затем B, независимо от успеха A

A && B # Выполните B тогда и только тогда, когда A завершился успешно

A || B # Выполните B тогда и только тогда, когда A не удалось

A & # Выполнить A в фоновом режиме.

Очень хорошее практическое правило. Я бы добавил, что в некоторых случаяхиспользование этих команд в подоболочке имеет смысл, когда мы хотим рассматривать их как единое целое или не хотим связывать результаты некоторых операций с текущей оболочкой.

Примеры:

-связать вывод двух команд:

(ls foo; ls bar) > single-result.txt

-вход в каталог и выполнить команду оттуда, не изменяя текущий каталог оболочки:

(cd target-directory && jar -xf ../my-jar)
5
ответ дан 10 October 2019 в 13:25

Престижность Шпаргалка Джека за то, что он четко и лаконично описывает, как это работает. Но у всех этих вещей есть более общая причина для выбора. Вам не нужно просто запоминать эти факты, когда вы делаете что-то в оболочке. В качестве дополнительного контекста вам также может быть интересно узнать, что:

  • ; обычно используется в качестве разделителя операторов в таких языках, как C, C ++, Perl, Java, C #, awk и множестве языков, которые были получены из те. Во всех этих случаях он выполняет одну и ту же функцию: делает одно, потом другое. Это похоже на точку в конце предложения.
  • & используется в C для побитового AND, поэтому && используется для логического AND. Логическое И в C включает в себя функцию, называемую сокращением. Сокращение означает, что для И, если первое неверно, нет причин проверять второе. Один ложный элемент в AND означает, что все будет ложным. В оболочке это означает, что он не перейдет ко второй команде, если первая не удалась. Или, если первое сработало, он перейдет ко второму, чтобы проверить, "может ли оно быть ложным".
  • | используется в C для побитового ИЛИ, поэтому || используется для логическое ИЛИ. Логические ИЛИ также имеют возможность быстрого доступа. В операционной это означает, что вы в первую очередь ищете истинную вещь. Так что, если первое не удастся, оно попробует второе.
4
ответ дан 4 January 2021 в 11:31

Другие вопросы по тегам:

Похожие вопросы: