скрипт bash для извлечения ВСЕХ совпадений с регулярным выражением - PullRequest
4 голосов
/ 04 сентября 2010

Я нашел это, но предполагается, что слова разделены пробелом.

result="abcdefADDNAME25abcdefgHELLOabcdefgADDNAME25abcdefgHELLOabcdefg"

for word in $result
do
    if echo $word | grep -qi '(ADDNAME\d\d.*HELLO)'
    then
        match="$match $word"
    fi
done

ОТПРАВЛЕНО

Переименование для ясности:

data="abcdefADDNAME25abcdefgHELLOabcdefgADDNAME25abcdefgHELLOabcdefg"
for word in $data
do
    if echo $word | grep -qi '(ADDNAME\d\d.*HELLO)'
    then
        match="$match $word"
    fi
done
echo $match

Оригинал оставлен, поэтому комментарии о result продолжают иметь смысл.

Ответы [ 3 ]

7 голосов
/ 04 сентября 2010

Редактировать: ответить на отредактированный вопрос:

for string in "$(echo $result | grep -Po "ADDNAME[0-9]{2}.*?HELLO")"
do
    match="${match:+$match }$string"
done

Оригинальный ответ:

Если вы используете Bash версии 3.2 или выше, вы можете использовать его соответствие регулярному выражению.

string="string to search 99 with 88 some 42 numbers"
pattern="[0-9]{2}"
for word in $string
do
    [[ $word =~ $pattern ]]
    if [[ ${BASH_REMATCH[0]} ]]
    then
        match="${match:+match }${BASH_REMATCH[0]}"
    fi
done

Результат будет "99 88 42".

4 голосов
/ 04 сентября 2010

Использование grep -o

-o, --only-match - показывать только часть строки, соответствующую ШАБЛОНУ

0 голосов
/ 05 сентября 2010

Не очень элегантно - и есть проблемы из-за жадного сопоставления - но это более или менее работает:

data="abcdefADDNAME25abcdefgHELLOabcdefgADDNAME25abcdefgHELLOabcdefg"
for word in $data \
    "ADDNAME25abcdefgHELLOabcdefgADDNAME25abcdefgHELLOabcdefg" \
    "ADDNAME25abcdefgHELLOabcdefgADDNAME25abcdefgHELLO"
do
    echo $word
done |
sed -e '/ADDNAME[0-9][0-9][a-z]*HELLO/{
        s/\(ADDNAME[0-9][0-9][a-z]*HELLO\)/ \1 /g
        }' |
while read line
do
    set -- $line
    for arg in "$@"
    do echo $arg
    done
done |
grep "ADDNAME[0-9][0-9][a-z]*HELLO"

Первый цикл отображает три строки данных - вы, вероятно, замените это на cat или перенаправление ввода / вывода.Сценарий sed использует модифицированное регулярное выражение для размещения пробелов вокруг шаблонов.Последний цикл разбивает слова, разделенные пробелом, на одно слово в строке.Последняя строка grep выбирает нужные вам строки.

Регулярное выражение изменяется с [a-z]* вместо исходного .*, поскольку сопоставление с образцом является жадным.Если данные между ADDNAME и HELLO не ограничены, вам следует подумать об использовании не жадных регулярных выражений, которые доступны в Perl и, возможно, Python и других современных языках сценариев:

#!/bin/perl -w
while (<>)
{
    while (/(ADDNAME\d\d.*?HELLO)/g)
    {
        print "$1\n";
    }
}

Это хорошая демонстрацияиспользования права тоже для работы.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...