2009-07-08 3 views
0

У меня проблема с регулярным выражением. Как можно написать следующее:Превращение требования соответствия строки в регулярное выражение

  1. начала с дополнительным уровнем доступа (цифра от 1 до 5)
  2. с последующим пробелом
  3. затем имя пользователя, состоящее из от 3 до 5 маленьких букв
  4. следует между 3 и 5 цифрами
  5. затем один или более пространствами
  6. , а затем четырехзначный пин-кодом
  7. затем один или более пространствами
  8. и тот же контактный снова для подтверждения ..

Если информация верна, отображать предупреждение о том, «Спасибо.» В противном случае «введенная информация неверна».

я написал следующее, но он не работает должным образом:

reg=/^(\d{1,5})?/s ([a-z]{3,5}\b\d{3,5}\s) \s\1 $/; 

Я был бы признателен за любую помощь.

+2

Было бы полезно, если бы вы приводили несколько примеров. что было бы легче понять, затем прочитав ваше описание – mkoryak

+1

ACK! Регулярное выражение! Убегай! Убегай! http://xkcd.com/208/ – bgw

+0

Это домашнее задание? – seth

ответ

0

попробовать это: ([1-5])?\s[a-z]{3,5}(\s*\d{4}){2}

+1

Ввод должен начинаться с пробела, если нет доступа levvel - я предполагаю, что это не является желаемым поведением. Далее вы не убедитесь, что оба номера контактов равны. –

+0

И \ s * делает пространство необязательным, хотя требуется хотя бы одно пространство, поэтому оно должно быть \ s +. –

+0

Оба истины! = D – Fernando

0

Это звучит, как вы хотите, первое место, даже если не указан уровень доступа? Если да, то я думаю, что это следует сделать трюк:

/^([1-5])? [a-z]{3,5}\d{3,5} +(\d{4}) +\2$/

Если пространство не является обязательным, просто переместить его в первый набор скобок.

Чтобы отобразить предупреждения, простое if/else должно это сделать.

+0

Я не думаю, что первый из них имеет длину от 1 до 5 цифр. Инструкции говорят «цифра от 1 до 5» – seth

+0

Да, я тоже сомневаюсь, но его пример и описание противоречивы. – annakata

+0

Упс, ты прав! Исправлено, спасибо. –

2

Несколько проблем я вижу сразу:

\d{1,5} будет соответствовать любой цифре (0-9) для 1 до 5 случаев. т.е. 0001, 12,3, 41332. Я думаю, что вы ищете [1-5], который будет соответствовать одной цифре в диапазоне от 1 до 5.

/s должен быть \s

с [a-z]{3,5}\b\d{3,5}\s Я не знаю, почему у вас есть \b там.

Устраните эти проблемы, прежде всего, я думаю.:)

+0

@ Джонатан: Спасибо за исправление кода, не знаю, что вы можете делать встроенные блоки кода :) – MitMaro

4

Ok, следуя вашим инструкциям к письму (который я не уверен, это то, что вы на самом деле хотите), вы можете использовать:

/^[1-5]?\s[a-z]{3,5}\d{3,5}\s+(\d{4})\s+(\1)$/ 

Ломая это вниз, это:

  • начало строки
  • одна цифра между 1 и 5, необязательно
  • пространство (строго говоря, любое пробельное пространство)
  • от 3 до 5 строчных букв
  • между 3 и 5 цифр
  • по меньшей мере одно пространство
  • ровно 4 цифры
  • по меньшей мере, одно пространство
  • по той же схеме из 4-х цифр (в \ 1 имеет решающее значение здесь)
  • конец строки

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

+0

'\ s' соответствует любым пробелам (например, вкладке), а не просто пробелам. В противном случае, пятно. –

+0

что делает '/ ^' делать? Я знаю, что это начало строки, но что такое /? это то, как делать regex в javascript? – Victor

+0

У вас есть несколько опечаток, возможно, редактирование в порядке. – Nixuz

0

Попробуйте это:

^(?:[1-5])?[a-z]{3,5}\d{3,5} +(\d{4}) +\1$ 

Вы могли бы найти my regex tool полезно для тестирования регулярных выражений. Он имеет режим «объяснения», который нарушит выражение и опишет, что он делает, если вы застряли.

Удачи вам!

+0

Я думаю, что уровень доступа вместе с пространством необязателен - это выражение заставляет начинать с пробела, если нет уровня доступа, следовательно ([0-5] _)? вместо ([0-5])? _ или [0-5]? _. –

+0

После повторного чтения, я думаю, вы должны быть правы. Я отредактировал исправление, но ваш ответ выглядит все равно. Благодаря! –

4
^(?:[1-5])?[a-z]{3,5}[0-9]{3,5} +([0-9]{4}) +\1$ 

Объяснение

 
    ^   Anchor start of line. 
    (?:[1-5])? Optional access level 1 to 5 followed by a single space, 
       the group is non-capturing. 
    [a-z]{3,5} User name with 3 to 5 lower case letters followed by 
    [0-9]{3,5} 3 to 5 digits. 
    _+   At least one space. 
    ([0-9]{4}) A 4 digit pin number captured into group \1. Without the 
       non-capturing group from above the pin number would be 
       captured into group \2. 
    _+   At least one space. 
    \1   A backreference to the pin number captured in group \1. 
    $   Anchor end of line. 
+1

Вы не использовали \ 1 в своем регулярном выражении. – SolutionYogi

+0

Спасибо, исправлено. –

+0

Вы не включили() для захвата [0-9] {4} в своем регулярном выражении. – Nefrubyr

-1

То, что вы описываете, это не обычный язык, поэтому он не может быть проанализирован с помощью регулярного выражения. Проблема заключается в ваших требованиях 6 и 8: регулярные выражения не имеют памяти, поэтому невозможно проверить, что PIN-коды в 6 и 8 идентичны.

+0

Конечно, это возможно, это называется «обратная ссылка». –

+0

@Pavel: Йорг теоретически правильный. То, что реализует практически любой полезный пакет, включает выражения, которые не являются «правильными» в теоретическом смысле, например. они используют группы захвата и обратные ссылки на них. Большинство людей используют «регулярное выражение» в довольно свободном смысле, и большинство меньшинства не волнуются об этом ;-) –

+0

В регулярных выражениях нет «обратной ссылки». Возможно, вы думаете о Regexps, которые иногда * делают * имеют обратные ссылки (а иногда и нет). Но ОП конкретно спрашивал о «регулярном выражении» и «не» о Regexp. Эти два совершенно разные вещи. В частности, регулярные выражения обычно намного мощнее, чем регулярные выражения. –

0

Вот ответ на Python, демонстрирующий объект re.VERBOSE, который очень удобен, если вы хотите вернуться завтра и понять, что делает ваше регулярное выражение.

См. this для более подробного объяснения. Вам не понадобится лоза или веревка, чтобы качаться. :-)

import re 
match_logon = re.compile(r""" 
    [1-5]?  # 1. start with an optional access level (a digit from 1 to 5) 
    [ ]   # 2. followed by a space 
    [a-z]{3,5} # 3. then a user name consisting of between 3 and 5 small letters 
    \d{3,5}  # 4. followed by between 3 and 5 digits 
    [ ]+  # 5. then one or more spaces 
    (\d{4,4}) # 6. and then a four digit pin number (captured for comparison) 
    [ ]+  # 7. then one or more spaces 
    \1   # 8. and the same pin again for confirmation.. 
    $   # match end of string 
    """, re.VERBOSE).match 
tests = [ 
    ("1 xyz123 9876 9876", True), 
    (" xyz123 9876 9876", True), # leading space? revisit requirement! 
    ("0 xyz123 9876 9876", False), 
    ("5 xyz123 9876 9876", False), # deliberate mistake to test the testing mechanism :-) 
    ("1 xy1234 9876 9876", False), 
    ("5 xyz123 9876 9875", False), 
    ("1 xyz123 9876 9876\0", False), 
    ] 
for data, expected in tests: 
    actual = bool(match_logon(data)) 
    print actual == expected, actual, expected, repr(data) 

Results: 
True True True '1 xyz123 9876 9876' 
True True True ' xyz123 9876 9876' 
True False False '0 xyz123 9876 9876' 
False True False '5 xyz123 9876 9876' 
True False False '1 xy1234 9876 9876' 
True False False '5 xyz123 9876 9875' 
True False False '1 xyz123 9876 9876\x00'