Флаг y позволÑÐµÑ Ð¿ÑоизвеÑÑи поиÑк на опÑеделÑнной позиÑии в иÑÑ
одной ÑÑÑоке.
ЧÑÐ¾Ð±Ñ ÑазобÑаÑÑ Ñлаг y и понÑÑÑ, Ñем же он Ñ
оÑоÑ, ÑаÑÑмоÑÑим пÑакÑиÑеÑкий пÑимеÑ.
Ðдна из ÑаÑÑо вÑÑÑеÑаÑÑÐ¸Ñ ÑÑ Ð·Ð°Ð´Ð°Ñ ÑегÑлÑÑнÑÑ Ð²ÑÑажений â лекÑиÑеÑкий ÑазбоÑ: Ð¼Ñ Ð¸Ð¼ÐµÐµÐ¼ ÑекÑÑ, напÑимеÑ, на каком-Ñо ÑзÑке пÑогÑаммиÑÐ¾Ð²Ð°Ð½Ð¸Ñ Ð¸ полÑÑаем его ÑÑÑÑкÑÑÑнÑе ÑлеменÑÑ.
ÐапÑимеÑ, в HTML еÑÑÑ Ñеги и аÑÑибÑÑÑ, в JavaScript-коде â пеÑеменнÑе и ÑÑнкÑии, и Ñ.п.
ÐÑ Ð½Ðµ бÑдем погÑÑжаÑÑÑÑ Ð³Ð»Ñбоко в ÑÐµÐ¼Ñ Ð½Ð°Ð¿Ð¸ÑÐ°Ð½Ð¸Ñ ÑÐ°ÐºÐ¸Ñ Ð°Ð½Ð°Ð»Ð¸Ð·Ð°ÑоÑов (ÑÑо ÑпеÑиализиÑÐ¾Ð²Ð°Ð½Ð½Ð°Ñ Ð¾Ð±Ð»Ð°ÑÑÑ Ñо Ñвоим набоÑом инÑÑÑÑменÑов и алгоÑиÑмов). Ðо в пÑоÑеÑÑе Ð¸Ñ ÑабоÑÑ, вообÑе, в пÑоÑеÑÑе анализа ÑекÑÑа, оÑÐµÐ½Ñ ÑаÑÑо Ð²Ð¾Ð·Ð½Ð¸ÐºÐ°ÐµÑ Ð·Ð°Ð´Ð°Ñа «пÑоÑиÑаÑÑ ÑÑо-Ñо на заданной позиÑии».
ÐапÑимеÑ, Ñ Ð½Ð°Ñ ÐµÑÑÑ ÑÑÑока кода let varName = "value", и нам надо пÑоÑиÑаÑÑ Ð¸Ð· Ð½ÐµÑ Ð¸Ð¼Ñ Ð¿ÐµÑеменной, коÑоÑое наÑинаеÑÑÑ Ñ Ð¿Ð¾Ð·Ð¸Ñии 4.
ÐÐ¼Ñ Ð¿ÐµÑеменной бÑдем иÑкаÑÑ ÐºÐ°Ðº Ñлово \w+. ÐообÑе, в ÑзÑке JavaScript Ð´Ð»Ñ Ð¸Ð¼ÐµÐ½Ð¸ пеÑеменной нÑжно ÑÑÑÑ Ð±Ð¾Ð»ÐµÐµ Ñложное ÑегÑлÑÑное вÑÑажение, но здеÑÑ ÑÑо не важно.
ÐÑзов str.match(/\w+/) найдÑÑ ÑолÑко пеÑвое Ñлово в ÑÑÑоке или вÑе Ñлова (Ñ Ñлагом g), а нам нÑжно одно Ñлово именно на позиÑии 4.
ÐÐ»Ñ Ð¿Ð¾Ð¸Ñка, наÑÐ¸Ð½Ð°Ñ Ñ Ð½Ñжной позиÑии, можно иÑполÑзоваÑÑ Ð¼ÐµÑод regexp.exec(str).
ÐÑли Ñ ÑегÑлÑÑного вÑÑÐ°Ð¶ÐµÐ½Ð¸Ñ regexp Ð½ÐµÑ Ñлагов g или y, Ñо ÑÑÐ¾Ñ Ð¼ÐµÑод иÑÐµÑ Ð¿ÐµÑвое Ñовпадение в ÑÑÑоке str, ÑоÑно Ñак же, как str.match(regexp). ÐдеÑÑ Ð½Ð°Ñ ÑÑÐ¾Ñ Ð¿ÑоÑÑейÑий ваÑÐ¸Ð°Ð½Ñ Ð±ÐµÐ· Ñлагов не инÑеÑеÑÑеÑ.
ÐÑли Ñлаг g еÑÑÑ, Ñо он оÑÑÑеÑÑвлÑÐµÑ Ð¿Ð¾Ð¸Ñк в ÑÑÑоке str, наÑÐ¸Ð½Ð°Ñ Ñ Ð¿Ð¾Ð·Ð¸Ñии, заданной ÑвойÑÑвом regexp.lastIndex. Ð, когда наÑ
одиÑ, обновлÑÐµÑ regexp.lastIndex на позиÑÐ¸Ñ Ð¿Ð¾Ñле ÑовпадениÑ.
ÐÑи Ñоздании ÑегÑлÑÑного вÑÑÐ°Ð¶ÐµÐ½Ð¸Ñ ÐµÐ³Ð¾ ÑвойÑÑво lastIndex Ñавно 0.
Так ÑÑо повÑоÑнÑе вÑÐ·Ð¾Ð²Ñ regexp.exec возвÑаÑаÑÑ ÑÐ¾Ð²Ð¿Ð°Ð´ÐµÐ½Ð¸Ñ Ð¿Ð¾ оÑеÑеди, одно за дÑÑгим.
ÐапÑÐ¸Ð¼ÐµÑ (Ñ Ñлагом g):
let str = 'let varName';
let regexp = /\w+/g;
alert(regexp.lastIndex); // 0 (пÑи Ñоздании lastIndex=0)
let word1 = regexp.exec(str);
alert(word1[0]); // let (пеÑвое Ñлово)
alert(regexp.lastIndex); // 3 (позиÑÐ¸Ñ Ð·Ð° пеÑвÑм Ñовпадением)
let word2 = regexp.exec(str);
alert(word2[0]); // varName (вÑоÑое Ñлово)
alert(regexp.lastIndex); // 11 (позиÑÐ¸Ñ Ð·Ð° вÑоÑÑм Ñовпадением)
let word3 = regexp.exec(str);
alert(word3); // null (болÑÑе Ñовпадений неÑ)
alert(regexp.lastIndex); // 0 (ÑбÑаÑÑваеÑÑÑ Ð¿Ð¾ оконÑании поиÑка)
ÐамеÑим, ÑÑо каждое Ñовпадение возвÑаÑаеÑÑÑ Ð² виде маÑÑива, Ñо вÑеми ÑкобоÑнÑми гÑÑппами и дополниÑелÑнÑми ÑвойÑÑвами.
Ðожно пеÑебÑаÑÑ Ð²Ñе ÑÐ¾Ð²Ð¿Ð°Ð´ÐµÐ½Ð¸Ñ Ð² Ñикле:
let str = 'let varName';
let regexp = /\w+/g;
let result;
while (result = regexp.exec(str)) {
alert( `Ðайдено ${result[0]} на позиÑии ${result.index}` );
// Ðайдено let на позиÑии 0, заÑем
// Ðайдено varName на позиÑии 4
}
Такое иÑполÑзование regexp.exec пÑедÑÑавлÑÐµÑ Ñобой алÑÑеÑнаÑÐ¸Ð²Ñ Ð¼ÐµÑÐ¾Ð´Ñ str.matchAll.
Таким обÑазом, поÑледоваÑелÑнÑе вÑÐ·Ð¾Ð²Ñ regexp.exec могÑÑ Ð½Ð°Ð¹Ñи вÑе ÑовпадениÑ, пÑедÑÑавлÑÑ Ñобой алÑÑеÑнаÑÐ¸Ð²Ñ Ð¼ÐµÑодам str.match/matchAll.
Ðо, в оÑлиÑие Ð¾Ñ Ð´ÑÑгиÑ
меÑодов, Ð¼Ñ Ð¼Ð¾Ð¶ÐµÐ¼ поÑÑавиÑÑ ÑамоÑÑоÑÑелÑно lastIndex, наÑав Ñем ÑамÑм поиÑк именно Ñ Ð½Ñжной позиÑии.
ÐапÑимеÑ, найдÑм Ñлово, наÑÐ¸Ð½Ð°Ñ Ñ Ð¿Ð¾Ð·Ð¸Ñии 4:
let str = 'let varName = "value"';
let regexp = /\w+/g; // без Ñлага g ÑвойÑÑво lastIndex игноÑиÑÑеÑÑÑ
regexp.lastIndex = 4;
let word = regexp.exec(str);
alert(word); // varName
ÐоиÑк \w+ пÑоизведÑн, наÑÐ¸Ð½Ð°Ñ Ñ Ð¿Ð¾Ð·Ð¸Ñии regexp.lastIndex = 4.
ÐамеÑим, ÑÑо Ñакой поиÑк лиÑÑ Ð½Ð°ÑинаеÑÑÑ Ñ Ð¿Ð¾Ð·Ð¸Ñии lastIndex и идÑÑ Ð´Ð°Ð»ÑÑе. ÐÑли Ñлова на позиÑии lastIndex неÑ, но оно еÑÑÑ Ð¿Ð¾Ð·Ð¶Ðµ, оно вÑÑ Ñавно бÑÐ´ÐµÑ Ð½Ð°Ð¹Ð´ÐµÐ½Ð¾:
let str = 'let varName = "value"';
let regexp = /\w+/g;
regexp.lastIndex = 3;
let word = regexp.exec(str);
alert(word[0]); // varName
alert(word.index); // 4
â¦Ð¢Ð¾ еÑÑÑ, пÑи Ñлаге g ÑвойÑÑво lastIndex задаÑÑ Ð½Ð°ÑалÑнÑÑ Ð¿Ð¾Ð·Ð¸ÑÐ¸Ñ Ð¿Ð¾Ð¸Ñка.
Флаг y заÑÑавлÑÐµÑ regexp.exec иÑкаÑÑ Ñовно на позиÑии lastIndex, ни до и ни поÑле.
ÐÐ¾Ñ ÑÐ¾Ñ Ð¶Ðµ поиÑк Ñ Ñлагом y:
let str = 'let varName = "value"';
let regexp = /\w+/y;
regexp.lastIndex = 3;
alert( regexp.exec(str) ); // null (на позиÑии 3 пÑобел, а не Ñлово)
regexp.lastIndex = 4;
alert( regexp.exec(str) ); // varName (Ñлово на позиÑии 4)
Ðак можно видеÑÑ, ÑегÑлÑÑное вÑÑажение /\w+/y не найдено на позиÑии 3 (в оÑлиÑие Ð¾Ñ Ñлага g), но найдено на позиÑии 4.
ÐÑедÑÑавим Ñебе, ÑÑо Ñ Ð½Ð°Ñ Ð±Ð¾Ð»ÑÑой ÑекÑÑ, и в нÑм Ð½ÐµÑ Ð½Ð¸ одного ÑовпадениÑ. Ð Ñаком ÑлÑÑае ÑегÑлÑÑное вÑÑажение Ñ Ñлагом g бÑÐ´ÐµÑ Ð¸Ð´Ñи до Ñамого конÑа ÑекÑÑа, и ÑÑо займÑÑ Ð³Ð¾Ñаздо болÑÑе вÑемени, Ñем поиÑк Ñ Ñлагом y.
РзадаÑаÑ
, подобнÑÑ
лекÑиÑеÑÐºÐ¾Ð¼Ñ Ð°Ð½Ð°Ð»Ð¸Ð·Ñ, обÑÑно много поиÑков на конкÑеÑной позиÑии. ÐÑполÑзование Ñлага y â клÑÑ Ðº Ñ
оÑоÑей пÑоизводиÑелÑноÑÑи.
ÐомменÑаÑии
<code>, Ð´Ð»Ñ Ð½ÐµÑколÑÐºÐ¸Ñ ÑÑÑок кода — Ñег<pre>, еÑли болÑÑе 10 ÑÑÑок — ÑÑÑÐ»ÐºÑ Ð½Ð° пеÑоÑниÑÑ (plnkr, JSBin, codepenâ¦)