Как условно сделать что-то если команда, за которой следуют или неудавшийся
Это точно что удар if
оператор делает:
if command ; then
echo "Command succeeded"
else
echo "Command failed"
fi
Добавление информации из комментариев: Вы не должны использовать [
... ]
синтаксис в этом случае. [
самостоятельно команда, очень почти эквивалентная test
. Это - вероятно, наиболее распространенная команда для использования в if
, который может привести к предположению, что это - часть синтаксиса оболочки. Но если Вы хотите протестировать, ли команда, за которой следуют или нет, используйте саму команду непосредственно с if
, как показано выше.
GNU grep имеет -P
опция для perl-стиля regexes, и -o
опция распечатать только, что соответствует шаблону. Они могут быть объединены с помощью, осматривают утверждения (описанный под Расширенными Шаблонами в perlre странице справочника) для удаления части grep шаблона от того, что полно решимости соответствовать в целях -o
.
$ grep -oP 'foobar \K\w+' test.txt
bash
happy
$
\K
краткая форма (и более эффективная форма) (?<=pattern)
который Вы используете в качестве нулевой ширины, оглядываются утверждение перед текстом, который Вы хотите произвести. (?=pattern)
может использоваться в качестве утверждения предвидения нулевой ширины после текста, который Вы хотите произвести.
Например, если Вы хотели распознать слово между foo
и bar
, Вы могли использовать:
$ grep -oP 'foo \K\w+(?= bar)' test.txt
или (для симметрии)
$ grep -oP '(?<=foo )\w+(?= bar)' test.txt
Стандарт grep не может сделать, это, но последние версии GNU grep может. Можно обратиться к sed, awk или жемчугу. Вот несколько примеров, которые делают то, что Вы хотите на своем демонстрационном входе; они ведут себя немного по-другому в угловых случаях.
Замена foobar word other stuff
word
, распечатайте, только если замена сделана.
sed -n -e 's/^foobar \([[:alnum:]]\+\).*/\1/p'
Если первое слово foobar
, распечатайте второе слово.
awk '$1 == "foobar" {print $2}'
Полоса foobar
если это - первое слово, и пропустите строку иначе; затем разделите все после первого пробела и печати.
perl -lne 's/^foobar\s+// or next; s/\s.*//; print'
grep
. Но синтаксис для этих команд на самом деле выглядит очень знакомым теперь, когда я знаком с поиском стиля энергии и заменой + regexes. Благодарит тонну.
– Cory Klein
20.05.2011, 02:51
grep
не имеет поддержки PCRE.
– Craig McQueen
17.03.2016, 02:12
Ну, если Вы знаете, что foobar всегда является первым словом или строкой, затем можно использовать сокращение. Как так:
grep "foobar" test.file | cut -d" " -f2
-o
включите grep, широко реализован (moreso, чем Гну grep расширения), таким образом делая grep -o "foobar" test.file | cut -d" " -f2
увеличит эффективность этого решения, которое является более портативным, чем использование lookbehind утверждения.
– dubiousjim
20.04.2012, 00:04
grep -o "foobar .*
"или grep -o "foobar \w+"
.
– G-Man Says 'Reinstate Monica'
14.04.2018, 10:20
Если PCRE не поддерживается, можно достигнуть того же результата с двумя вызовами grep. Например, для захвата слова после того, как foobar делают это:
<test.txt grep -o 'foobar *[^ ]*' | grep -o '[^ ]*$'
Это может быть расширено до произвольного слова после foobar как это (с EREs для удобочитаемости):
i=1
<test.txt egrep -o 'foobar +([^ ]+ +){'$i'}[^ ]+' | grep -o '[^ ]*$'
Вывод:
1
Отметьте индекс i
основано на нуле.
sed -n "s/^.*foobar\s*\(\S*\).*$/\1/p"
-n suppress printing
s substitute
^.* anything before foobar
foobar initial search match
\s* any white space character (space)
\( start capture group
\S* capture any non-white space character (word)
\) end capture group
.*$ anything after the capture group
\1 substitute everything with the 1st capture group
p print it
pcregrep
имеет более умный вариант -o
который позволяет вам выбрать, какие группы захвата вы хотите вывести. Итак, используя ваш файл примера,
$ pcregrep -o1 "foobar (\w+)" test.txt
bash
happy
Мне очень помог ответ @jgshawkey. grep
не такой уж хороший инструмент для этого, но sed подойдет, хотя здесь у нас есть пример, который использует grep для захвата соответствующей строки.
Синтаксис sed в регулярных выражениях уникален, если вы к нему не привыкли.
Вот еще один пример :этот анализирует вывод xinput для получения целочисленного идентификатора
⎜ ↳ SynPS/2 Synaptics TouchPad id=19 [slave pointer (2)]
а я хочу 19
export TouchPadID=$(xinput | grep 'TouchPad' | sed -n "s/^.*id=\([[:digit:]]\+\).*$/\1/p")
Обратите внимание на синтаксис класса:
[[:digit:]]
и необходимость избежать следующего+
Я предполагаю, что совпадает только одна строка.
sed(1)
– camh 23.03.2013, 00:51grep -oP 'foobar \K\w+' test.txt
ничего не производит с OP'stest.txt
. grep версия 2.5.1. Что могло быть неправильным? O_O – SOUser 24.07.2014, 17:19