Grep регулярное выражение для цифр в символьной строке переменной длины - PullRequest
2 голосов
/ 08 декабря 2009

Мне нужен какой-то способ найти слова, которые содержат любую комбинацию символов и цифр, но точно 4 цифры только и хотя бы один символ.

Пример:

a1a1a1a1        // Match
1234            // NO match (no characters)
a1a1a1a1a1      // NO match
ab2b2           // NO match
cd12            // NO match
z9989           // Match
1ab26a9         // Match
1ab1c1          // NO match
12345           // NO match
24              // NO match
a2b2c2d2        // Match
ab11cd22dd33    // NO match

Ответы [ 9 ]

3 голосов
/ 08 декабря 2009

чтобы соответствовать цифре в grep, вы можете использовать [0-9]. Чтобы сопоставить что-либо, кроме цифры, вы можете использовать [^ 0-9]. Так как это может быть любое количество символов или без символов, вы добавляете «*» (любое число предыдущего). Итак, что вы хотите, это логически

(anything not a digit or nothing)* (any single digit) (anything not a digit or nothing)* . ...

до тех пор, пока у вас не будет 4 группы "любая цифра". то есть [^ 0-9] * [0-9] ...

Я обнаружил, что с длинными шаблонами grep, особенно с длинными цепочками специальных символов, которые нужно экранировать, лучше создавать медленно, поэтому вы уверены, что понимаете, что происходит. Например,

#this will highlight your matches, and make it easier to understand
alias grep='grep --color=auto'
echo 'a1b2' | grep '[0-9]' 

покажет вам, как это соответствует. Затем вы можете расширить шаблон, как только вы поймете каждую часть.

2 голосов
/ 08 декабря 2009

Я не уверен во всех других вводимых вами данных (т. Е. ax12ax12ax12ax12 действителен?), Но это будет работать в зависимости от того, что вы опубликовали:

%> grep -P "^(?:\w\d){4}$" fileWithInput
1 голос
/ 08 декабря 2009

Если вы не против использовать небольшую оболочку, вы можете сделать что-то вроде этого:

echo "a1a1a1a1" |grep -o '[0-9]'|wc -l

, который будет отображать количество цифр, найденных в строке. Если хотите, вы можете проверить на данное количество совпадений:

max_match=4
[ "$(echo "a1da4a3aaa4a4" | grep -o '[0-9]'|wc -l)" -le $max_match ] || echo "too many digits."
0 голосов
/ 09 декабря 2009

спасибо за ваши ответы наконец, я написал сценарий, и он отлично работает: , / P ab2b2 cd12 z9989 1ab26a9 1ab1c1 1234 24 a2b2c2d2

#!/bin/bash
echo "$@" |tr -s " " "\n"s >> sorting
cat sorting | while read tostr
do
  l=$(echo $tostr|tr -d "\n"|wc -c)
  temp=$(echo $tostr|tr -d a-z|tr -d "\n" | wc -c)

  if [ $temp -eq 4 ]; then
    if [ $l -gt 4 ]; then
      printf "%s " "$tostr"
    fi
  fi
done
echo
0 голосов
/ 08 декабря 2009

Вы можете использовать обычный сценарий оболочки, без необходимости сложных регулярных выражений.

var=a1a1a1a1
alldigits=${var//[^0-9]/}
allletters=${var//[0-9]/}
case "${#alldigits}" in
   4)
    if [ "${#allletters}" -gt 0 ];then
        echo "ok: 4 digits and letters: $var"
    else
        echo "Invalid: all numbers and exactly 4: $var"
    fi
    ;;
   *) echo "Invalid: $var";;
esac
0 голосов
/ 08 декабря 2009

Регулярное выражение для этого:

([A-Za-z]\d){4}
  • [A-Za-z] - для класса персонажей
  • \ d - для номера
  • Вы оборачиваете их в (), чтобы сгруппировать их, указывая символ формата, следующий за номером
  • {4} - указывает, что должно быть 4 повторения
0 голосов
/ 08 декабря 2009

Вы можете попробовать

[^0-9]*[0-9][^0-9]*[0-9][^0-9]*[0-9][^0-9]*[0-9][^0-9]*

Но это будет соответствовать 1234. Почему это не соответствует вашим критериям?

0 голосов
/ 08 декабря 2009

Если вам нужен только ASCII, и вы можете получить доступ только к (довольно примитивным) конструкциям регулярных выражений grep, следующее должно быть довольно близко:

grep ^[a-zA-Z]*[0-9][a-zA-Z]*[a-zA-Z]*[0-9][a-zA-Z]*[a-zA-Z]*[0-9][a-zA-Z]*[a-zA-Z]*[0-9][a-zA-Z]*$ | grep [a-zA-Z]
0 голосов
/ 08 декабря 2009

С grep:

grep -iE '^([a-z]*[0-9]){4}[a-z]*$' | grep -vE '^[0-9]{4}$'

Сделайте это одним паттерном с Perl:

perl -ne 'print if /^(?!\d{4}$)([^\W\d_]*\d){4}[^\W\d_]*$/'

Классный [^\W\d_] класс символов - космополитический способ написания [A-Za-z]: он ловит все буквы, а не только английские.

...