Paranteze non-capturante în expresiile regulate PHP

Parantezele () îndeplinesc două funcții - gruparea caracterelor și funcția de captură (grup de captură). Și ce facem dacă trebuie să grupăm, dar să nu capturăm? Pentru a rezolva această problemă au fost create paranteze non-capturante (?: ) - ele grupează, dar nu capturează.

Exemplu

În exemplul următor, primele paranteze ne sunt necesare pentru grupare, iar cele doua - pentru captură. Cu toate acestea, ambele tipuri de paranteze salvează date în grupurile de captură:

php<?php
  $str = 'abab123';
  $reg = '#(ab)+([1-9]+)#';
  preg_match_all($reg, $str, $res);
?>

Ca rezultat, în grupurile noastre de captură va fi următoarele:

php<?php
  var_dump($res[0]); // va afișa 'abab123'
  var_dump($res[1]); // va afișa 'ab'
  var_dump($res[2]); // va afișa '123'
?>

Exemplu

Să facem astfel încât prima pereche de paranteze să doar grupeze, dar să nu captureze:

php<?php
  $str = 'abab123';
  $reg = '#(?:ab)+([1-9]+)#';
  preg_match_all($reg, $str, $res);
?>

Ca rezultat, în primul grup de captură va fi numărul nostru:

php<?php
  var_dump($res[1]); // va afișa '123'
?>

Sarcini practice

Задание 1

Sunt date subșiruri, împărțite în două părți de un număr arbitrar de perechi $@:

php<?php
  $str = 'aaa$@bbb aaa$@$@bbb aaa$@$@$@bbb';
?>

Găsiți fiecare astfel de subșir și pentru fiecare subșir găsit, puneți în primul grup de captură ceea ce se află înainte de separator, iar în al doilea grup de captură - ceea ce se află după separator.