Как я могу отрицать возвращаемое значение процесса?
Я ищу простой, но кросс-платформенный отрицание-процесс, который отрицает значение, возвращаемое процессом. Он должен сопоставить 0 с некоторым значением != 0 и любом значении != 0 к 0, т. е. следующая команда должна возвращать "да, несуществующий путь не существует":
ls nonexistingpath | negate && echo "yes, nonexistingpath doesn't exist."
The ! - оператор велик, но, к сожалению, не является независимым от оболочки.
5 ответов:
ранее ответ был представлен с тем, что теперь первый раздел как последний раздел.
оболочка POSIX включает в себя
!
операторковыряясь в спецификации оболочки для других проблем, я недавно (сентябрь 2015) заметил, что оболочка POSIX поддерживает
!
оператора. Например, он указан как зарезервированное слово и может появиться в начале трубопровод - где a простая команда является частным случаем "конвейера". Поэтому его можно использовать вif
заявления иwhile
илиuntil
петли тоже - в POSIX-совместимых оболочках. Следовательно, несмотря на мои оговорки, он, вероятно, более широко доступен, чем я понял еще в 2008 году. Быстрая проверка POSIX 2004 и SUS / POSIX 1997 показывает, что!
присутствовал в обеих этих версий.отметим, что
!
оператор должен явиться в начало газопровода и отрицает код состояния всего конвейера (т. е. последние). Вот несколько примеров.# Simple commands, pipes, and redirects work fine. $ ! some-command succeed; echo $? 1 $ ! some-command fail | some-other-command fail; echo $? 0 $ ! some-command < succeed.txt; echo $? 1 # Environment variables also work, but must come after the !. $ ! RESULT=fail some-command; echo $? 0 # A more complex example. $ if ! some-command < input.txt | grep Success > /dev/null; then echo 'Failure!'; recover-command; mv input.txt input-failed.txt; fi Failure! $ ls *.txt input-failed.txt
портативный ответ-работает с античными раковинами
в сценарии Bourne (Korn, POSIX, Bash) я использую:
if ...command and arguments... then : it succeeded else : it failed fi
это как портативный, как он получает. "Команда и аргументы" могут быть конвейером или другой составной последовательностью команд.
A
not
командаThe'! оператора, встроенная в ваша оболочка или предоставленная o / s, не является универсально доступной. Это не ужасно трудно написать, хотя-код ниже восходит по крайней мере к 1991 году (хотя я думаю, что написал предыдущую версию еще раньше). Я не склонен использовать это в своих сценариях, хотя, потому что это не надежно доступно.
/* @(#)File: $RCSfile: not.c,v $ @(#)Version: $Revision: 4.2 $ @(#)Last changed: $Date: 2005/06/22 19:44:07 $ @(#)Purpose: Invert success/failure status of command @(#)Author: J Leffler @(#)Copyright: (C) JLSS 1991,1997,2005 */ #include <stdlib.h> #include <unistd.h> #include <sys/types.h> #include <sys/wait.h> #include "stderr.h" #ifndef lint static const char sccs[] = "@(#)$Id: not.c,v 4.2 2005/06/22 19:44:07 jleffler Exp $"; #endif int main(int argc, char **argv) { int pid; int corpse; int status; err_setarg0(argv[0]); if (argc <= 1) { /* Nothing to execute. Nothing executed successfully. */ /* Inverted exit condition is non-zero */ exit(1); } if ((pid = fork()) < 0) err_syserr("failed to fork\n"); if (pid == 0) { /* Child: execute command using PATH etc. */ execvp(argv[1], &argv[1]); err_syserr("failed to execute command %s\n", argv[1]); /* NOTREACHED */ } /* Parent */ while ((corpse = wait(&status)) > 0) { if (corpse == pid) { /* Status contains exit status of child. */ /* If exit status of child is zero, it succeeded, and we should exit with a non-zero status */ /* If exit status of child is non-zero, if failed and we should exit with zero status */ exit(status == 0); /* NOTREACHED */ } } /* Failed to receive notification of child's death -- assume it failed */ return (0); }
это возвращает "успех", противоположный неудаче, когда он не может выполнить команду. Мы можем обсудить, был ли правильным вариант "ничего не делать успешно"; возможно, это должен сообщить об ошибке, когда его не просят ничего делать. Код в '
"stderr.h"
' предоставляет простые средства сообщения об ошибках-я использую его везде. Исходный код по запросу-см. мою страницу профиля, чтобы связаться со мной.
в Баш, используйте ! оператор перед командой. Например:
! ls nonexistingpath && echo "yes, nonexistingpath doesn't exist"
вы можете попробовать:
ls nonexistingpath || echo "yes, nonexistingpath doesn't exist."
или так:
! ls nonexistingpath