Припустимо, у нас є рядок +38(067)-123-45-67
і нам потрібно знайти всі числа в ньому. Але цього разу, на відміну від попередніх, нас цікавлять не поодинокі цифри, а саме числа : 38, 067, 123, 45, 67
.
Число це послідовність з 1, або більше цифр \d
і щоб позначити потрібну нам кількість, ми можемо застосувати квантифікатор.
Кількість {n}
Найпростішим квантифікатором є число у фігурних дужках: {n}
.
Квантифікатор додається до символу(або класу символів, набору [...]
, тощо) і позначає яка їх кількість нам потрібна.
Існує декілька способів використання квантифікатора, розглянемо на прикладах:
- Точна кількість:
{5}
-
\d{5}
означає точно 5 цифр, так само як і\d\d\d\d\d
.Нижченаведений приклад шукатиме число, яке складається з 5-ти цифр:
alert
(
"Мені 12345 років"
.
match
(
/
\d{5}
/
)
)
;
// "12345"
Ми могли б додати
\b
і таким чином вилучити з пошуку числа довші за наш шаблон:\b\d{5}\b
. - Діапазон:
{3,5}
, від 3 до 5 -
Щоб знайти числа, які складаються з мінімум 3 і максимум 5 чисел, ми можемо вказати потрібні обмеження у фігурних дужках:
\d{3,5}
alert
(
"Мені не 12 років, а 1234"
.
match
(
/
\d{3,5}
/
)
)
;
// "1234"
Ми можемо не вказувати верхню межу.
В такому випадку, регулярний вираз
\d{3,}
шукатиме послідовність цифр довжиною від3
і/або більше:alert
(
"Мені не 12, а 345678 років"
.
match
(
/
\d{3,}
/
)
)
;
// "345678"
Давайте повернемось до рядка +38(067)-123-45-67
.
Число це послідовність з однієї або більше цифр підряд. Таким чином, регулярний вираз виглядатиме \d{1,}
:
let
str =
"+38(067)-123-45-67"
;
let
numbers =
str.
match
(
/
\d{1,}
/
g
)
;
alert
(
numbers)
;
// 38,067,123,45,67
Скорочення
Існують способи скорочено записати більшу частину часто вживаних квантифікаторів:
+
-
Означає “один, або більше”, так само як і
{1,}
.До прикладу,
\d+
шукає числа, які складаються з однієї, або більше цифр:let
str=
"+38(067)-123-45-67"
;
alert
(
str.
match
(
/
\d+
/
g
)
)
;
// 38,067,123,45,67
?
-
Означає “нуль, або один”, так само як і
{0,1}
. Інакше кажучи, в такий спосіб ми робимо символ необов’язковим.До прикладу, шаблон
ou?r
шукатиме літеруo
після якої, можливо, йтиме літераu
, і потім літераr
.І таким чином,
colou?r
знайде обидва словаcolor
таcolour
:let
str=
"Англійською слово колір пишеться як color чи colour?"
;
alert
(
str.
match
(
/
colou?r
/
g
)
)
;
// color, colour
*
-
Означає “нуль, або більше”, так само, як і
{0,}
. Це означає, що символ може бути відсутнім, або повторюватись безліч разів.До прикладу,
\d0*
шукає цифру, після якої йде будь-яка кількість нулів (може бути багато, або жодного):alert
(
"100 10 1"
.
match
(
/
\d0*
/
g
)
)
;
// 100, 10, 1
Порівняйте з
+
(один, або більше):alert
(
"100 10 1"
.
match
(
/
\d0+
/
g
)
)
;
// 100, 10
// Регулярний вираз не знайшов 1, оскільки 0+ вимагає наявності щонайменше одного нуля
Більше прикладів
Квантифікатори використовуються дуже часто. Вони основні “будівельні блоки” складних регулярних виразів, тож розглянемо ще декілька прикладів.
Регулярний вираз для десяткових дробів (чисел з плаваючою комою): \d+\.\d+
В дії:
alert
(
"0 1 12.345 7890"
.
match
(
/
\d+\.\d+
/
g
)
)
;
// 12.345
Регулярний вираз для “відкриваючого HTML-тегу без атрибутів”, наприклад, <span>
, або <p>
.
-
Найпростіший варіант:
/<[a-z]+>/i
alert
(
"<body> ... </body>"
.
match
(
/
<[a-z]+>
/
gi
)
)
;
// <body>
Регулярний вираз шукає символ
'<'
після якого йдуть одна, або більше літер латиницею, а потім'>'
. -
Покращений варіант:
/<[a-z][a-z0-9]*>/i
Згідно стандарту, назва HTML-тегу може містити в собі і цифру на будь-якій позиції окрім першої, як наприклад
<h1>
.alert
(
"<h1>Hi!</h1>"
.
match
(
/
<[a-z][a-z0-9]*>
/
gi
)
)
;
// <h1>
Регулярний вираз “відкриваючого, або закриваючого HTML-тегу без атрибутів”: /<\/?[a-z][a-z0-9]*>/i
Ми додали необов’язковий слеш /?
на початку шаблону і для того, щоб JavaScript не сприйняв його як кінець регулярного виразу, нам довелось його екранувати.
alert
(
"<h1>Hi!</h1>"
.
match
(
/
<\/?[a-z][a-z0-9]*>
/
gi
)
)
;
// <h1>, </h1>
На прикладах ми побачили, що більш точним є регулярний вираз, тим довшим і складнішим є його реалізація.
До прикладу, для HTML-тегів без атрибутів ми могли б використати простіший регулярний вираз: <\w+>
. Але так як HTML має більш жорсткі вимоги до назв тегів, то шаблон <[a-z][a-z0-9]*>
буде більш точним.
Чи можемо ми використовувати <\w+>
чи краще писати <[a-z][a-z0-9]*>
?
В реальному життя обидва варіанти мають право на існування. Все залежить від того, чи готові ми допустити “зайві” співпадіння з нашим регулярний виразом і наскілльки важко, або легко буде відфільтрувати їх і отримати перелік потрібних нам співпадінь.
Коментарі
<code>
, для кількох рядків – обгорніть їх тегом<pre>
, для понад 10 рядків – використовуйте пісочницю (plnkr, jsbin, codepen…)