Как получить статус выхода при использовании команды sed?


11

Команда grepвыдает статус выхода:

$echo "foo.bar" | grep -o foo
foo
$echo $?
0
$echo "foo.bar" | grep -o pop
$echo $?
1  

Но мне нужно использовать, sedи я понял, что у него нет статуса выхода:

$echo "foo.bar" | sed 's/bar.*$//'
foo.
$echo $?
0
$echo "foo.bar" | sed 's/pop.*$//'
foo.bar
$echo $?
0  

Я знаю, что я должен поиграть с -qопцией, но мне это не удалось.


7
Обратите внимание, что sedнаверняка имеет статус выхода, он просто не делает то, что вам нужно здесь. Если sedкоманда не выполнена, например, если вы попытаетесь запустить ее для файла, к которому у вас нет прав на запись или который не существует, sedпроизойдет выход со статусом выхода, отличным от 0. Статус выхода просто указывает, sedудалось ли вам выполнить то, что вы ему сказали, и echo "foo.bar" | sed 's/pop.*$//'был ли он правильно выполнен. Он удалил все строки с pop. То, что таких строк не было, не имеет значения, команда все еще работала.
Тердон

@Zanna Я собирался опубликовать ответ, но я чувствовал, что это на самом деле не отвечает на вопрос. Это только объясняет заблуждение, но не предоставляет полезного решения, как у стилдрайвера ниже. Так что комментарий показался более уместным.
тердон

Ответы:


13

Вы можете использовать q n для выхода со статусом выхода n - но для того, чтобы сделать это полезным, вам также нужно будет использовать некоторые функции ветвления и управления потоком :

т
ветвь условно (то есть: переход к метке) , только если s/// команда преуспела с момента последней строке ввода был прочитан или другой условный переход был взят.

Вероятно, лучше выбрать значение для n , которое отличается от одного из стандартных значений состояния выхода:

Нулевое состояние выхода указывает на успех, а ненулевое значение указывает на сбой. GNU 'sed' возвращает следующие значения ошибки состояния выхода:

0
 Successful completion.

1
 Invalid command, invalid syntax, invalid regular expression or a
 GNU 'sed' extension command used with '--posix'.

2
 One or more of the input file specified on the command line could
 not be opened (e.g.  if a file is not found, or read permission is
 denied).  Processing continued with other files.

4
 An I/O error, or a serious processing error during runtime, GNU
 'sed' aborted immediately.

Так например

$ echo "foo.bar" | sed 's/bar.*$//; t; q42' ; echo $? 
foo.
0

в то время как

$ echo "foo.bar" | sed 's/baz.*$//; t; q42' ; echo $? 
foo.bar
42

Если вы хотите опустить печать по умолчанию пространства шаблона, то замените qна Q(обратите внимание, что Qэто расширение GNU).


1

Вот как найти регулярное выражение с помощью sed и выделить совпадения или вернуть код выхода (5), если совпадений не найдено:

Это input.txt:

hello there
my dear old friend
a lot of things
we'll pass along the end

Вот моя функция: распечатать все + выделить совпадения + код возврата:

highlight()
{
  pattern=$1
  shift
  sed '/'"${pattern}"'/,${s//\x1b[32m&\x1b[0m/g;b};$q5' "$@"
}

$ highlight "lo \ | end" input.txt || echo -e "\ n * Ничего не найдено *"

Хель вот там
мой дорогой старые ПТ конец
а л т вещей ,
мы будем передавать ли нг на конце

Когда нет совпадения, он вернет код выхода (5). Вы можете использовать его с кошкой и трубой | также:

$ cat input.txt | выделить "горячие \ | и" || echo -e "\ n * Ничего не найдено *"

привет
мой дорогой старый друг
много вещей ,
мы проедем вдоль конца

* Совпадение не найдено *

Благодаря https://unix.stackexchange.com/a/405725/43233 - я использую опцию + sed quit.

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.