Як я можу запустити кілька команд, які мають & в одному командному рядку?


12

У мене виникли проблеми з головним болем.

Я хочу виконувати команди mulitple у фоновому режимі, тому я хочу запускати їх у bash по черзі. Запустити одну команду в оболонці Linux у фоновому режимі просто так:

myCommand &

Також легко запустити декілька команд, так само:

myCommand1 && myCommand2

або

myCommand1 ; myCommand2

Але якщо я хочу запустити кілька команд у фоновому режимі, я спробував такий формат команд, але не вдався:

myCommand1 & && myCommand2 &

або

myCommand1 & ; myCommand2 &

Обидва формати виходять з ладу. Як я можу запустити кілька команд, які є &в одному командному рядку?


2
Покладіть їх у сценарій та запустіть сценарій у фоновому режимі
Пантера



Пантера, схоже, використання () може допомогти виправити цю проблему набагато простіше, ніж використання сценарію. Спробуємо спочатку повністю використати функції, які надає сама оболонка, а не складати те, що ми хочемо самі. Але звичайно, використання скрипту також може виправити цю проблему. Все одно, дякую.
Годинник ЧОНГ

Що робити, якщо я хочу запустити "хвіст -F <file1>> <файл2>", а потім "завдання -l", після чого знову слід "відхилити -h% 1"
akskap

Відповіді:


24

Використовуйте ().

Якщо ви хочете запустити їх послідовно:

(myCommand1; myCommand2) &

або

(myCommand1 &) && (myCommand2 &)

Якщо ви хочете, щоб вони виконувались паралельно:

myCommand1 & myCommand2 &

У bash ви також можете скористатися цим (пробіл за {і the; є обов'язковими):

{ myCommand1 && myCommand2; } &

3
(myCommand1 &) && (myCommand2 &)буде працювати myCommand2навіть у разі myCommand1невдачі.
тердон

() може допомогти Башу розрізнити & і &&. Тому просто використовуйте (), щоб відокремити блок виконання, коли ми хочемо використовувати перемикач & і &&.
Годинник ZHONG

16

Я думаю, ви хочете цього:

myCommand1 & myCommand2 &

Це запускається myCommand1і надсилає його на другий план, після якого слідує амперсанд, потім негайно запускається myCommand2і відправляється також на задній план, тому вивільняючи оболонку знову.

Списки

Для кращого розуміння ви можете замінити трубопровід з допомогою команди тут.

Список - це послідовність одного або декількох трубопроводів, розділених одним з операторів ; , & , && або || , і необов'язково припиняється одним із ; , & , або .

Якщо команду припиняє оператор управління & , оболонка виконує команду у фоновому режимі в нижній частині. Оболонка не чекає завершення команди, а стан повернення - 0. Команди, розділені а ; виконуються послідовно; оболонка чекає, коли кожна команда завершиться по черзі. Статус повернення - це стан виходу останньої виконаної команди.

Списки AND і OR - це послідовності одного або декількох трубопроводів, розділених && та || оператори управління відповідно.
Джерело:man bash

Розбимо це на приклади. Список можна створити, комбінуючи команди та відокремивши їх однією з таких ; & && ||:

command1 ; command2  # runs sequentially
command1 && command2 # runs sequentially, runs command2 only if command1 succeeds
command1 || command2 # runs sequentially, runs command2 only if command1 fails
command1 & command2  # runs simultaneously

Ви можете припинити списки з одним з них: ; & <newline>.
Зазвичай ви виконуєте команду або список, натискаючи Enter, що дорівнює <newline>. Точка з комою ;служить тій самій цілі, особливо в сценаріях. Ampersand, &однак, запускає команди (и) у піддіаграмі на задньому плані, негайно звільняючи оболонку.

Ви можете використовувати круглі ()або фігурні дужки {}для подальших списків груп, різниця полягає в тому, що круглі дужки породять нижню частину, а фігурні - ні. Фігурним дужкам потрібний пробіл після першого та крапки з комою або новою лінією перед дужкою, що закривається. Наприклад:

# if c1 succeeds start a shell in the background
# and run c2 and c3 sequentially inside it
c1 && ( c2 ; c3 ) & 
# run c1 and if it succeeds c2 sequentially as a group command
# if c1 or c2 fail run c3 in the background
{ c1 && c2 ;} || c3 &

Це може стати досить складним, якщо ви не впевнені у використанні trueта falseперевірити, чи працює будівництво так, як очікувалося:

$ { true && true ;} || echo 2
$ { true && false ;} || echo 2
2

Контроль роботи

У jobsкоманді відображає список фонових завдань, які працюють або недавно закінчили в поточній оболонці. Існує ряд комбінацій клавіш та команд для управління роботою:

  • Ctrl+ Zвводить символ призупинення, який змушує зупинити процес, який зараз працює на передньому плані, він не припиняється, але залишається у jobsсписку
  • Ctrl+ Yвводить символ відкладеної зупинки, який змушує зупинити процес, який зараз працює на передньому плані, коли він намагається прочитати вхід з терміналу
  • fg= %виводить процес на перший план, запускаючи його, якщо потрібно, ви можете вказати процес наступним чином:

     %       # last process in the jobs list
     %1      # 1st process in the jobs list
     %abc    # process beginning with the string “abc”
     %?abc   # process containing the string “abc” anywhere
    
  • bg= %&приймає процес на задній план, запускаючи його, якщо потрібно:

     %&      # last process in the jobs list
     %1&     # 1st process in the jobs list
     %abc&   # process beginning with the string “abc”
     %?abc&  # process containing the string “abc” anywhere
    
  • wait чекає закінчення фонового процесу і повертає його статус припинення:

     wait %1 # 1st process in the jobs list

    Уявіть, що ви розпочали тривалий процес ( jobsвиявляє, що це номер 3), а потім зрозумійте, що ви хочете призупинити роботу комп'ютера після його завершення, а echoтакож повідомлення, якщо процес не вдався:

     wait %3 || echo failed ; systemctl suspend

Але важливо бути обережними з &&, це залежить від того, що повертається команда , тому ми повинні бути впевнені, що те, що ми називаємо, насправді повертає щось bash, вважаючи триєдним значенням ..?
mathreadler

@mathreadler Якщо ви не говорите про погано зроблений сценарій користувача, значення виходу дуже чітко визначено (див. man bash) і широко використовується саме так, як це призначено AFAIK - я ніколи не відчував нічого дивного.
десерт

саме слід бути обережним щодо погано складених сценаріїв користувачів. Вони існують і можуть неприємно знайти таких помилок. Askubuntu не дозволяє мені "@ десертувати" тебе.
mathreadler

Ну добре, це має сенс зараз, коли ви це згадуєте.
mathreadler
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.