note 127718 added to regexp.reference.back-references

From: Date: Wed, 12 Oct 2022 21:22:25 +0000
Subject: note 127718 added to regexp.reference.back-references
Groups: php.notes 
Request: Send a blank email to php-notes+get-219668@lists.php.net to get a copy of this message
The escape sequence \g used as a backreference may not always behave as expected. The following numbered backreferences refer to the text matching the specified capture group, as documented: \1 \g1 \g{1} \g-1 \g{-1} However, the following variants refer to the subpattern code instead of the matched text: \g<1> \g'1' \g<-1> \g'-1' With named backreferences, we may also use the \k escape sequence as well as the (?P=...) construct. The following combinations also refer to the text matching the named capture group, as documented: \g{name} \k{name} \k<name> \k'name' (?P=name) However, these refer to the subpattern code instead of the matched text: g<name> \g'name' In the following example, the capture group searches for a single letter 'a' or 'b', and then the backreference looks for the same letter. Thus, the patterns are expected to match 'aa' and 'bb', but not 'ab' nor 'ba'. <?php /* Matches to the following patterns are replaced by 'xx' in the subject string 'aa ab ba bb'. */ $patterns = [ # numbered backreferences (absolute) '/([ab])\1/', // 'xx ab ba xx' '/([ab])\g1/', // 'xx ab ba xx' '/([ab])\g{1}/', // 'xx ab ba xx' '/([ab])\g<1>/', // 'xx xx xx xx' # unexpected behavior, backreference matches both 'a' and 'b'. "/([ab])\g'1'/", // 'xx xx xx xx' # unexpected behavior, backreference matches both 'a' and 'b'. '/([ab])\k{1}/', // 'aa ab ba bb' # No group with name "1", backreference to unset group always fails. '/([ab])\k<1>/', // 'aa ab ba bb' # No group with name "1", backreference to unset group always fails. "/([ab])\k'1'/", // 'aa ab ba bb' # No group with name "1", backreference to unset group always fails. '/([ab])(?P=1)/', // NULL # Regex error: "subpattern name must start with a non-digit", (?P=) expects name not number. # numbered backreferences (relative) '/([ab])\-1/', // 'aa ab ba bb' '/([ab])\g-1/', // 'xx ab ba xx' '/([ab])\g{-1}/', // 'xx ab ba xx' '/([ab])\g<-1>/', // 'xx xx xx xx' # unexpected behavior, backreference matches both 'a' and 'b'. "/([ab])\g'-1'/", // 'xx xx xx xx' # unexpected behavior, backreference matches both 'a' and 'b'. '/([ab])\k{-1}/', // 'aa ab ba bb' # No group with name "-1", backreference to unset group always fails. '/([ab])\k<-1>/', // 'aa ab ba bb' # No group with name "-1", backreference to unset group always fails. "/([ab])\k'-1'/", // 'aa ab ba bb' # No group with name "-1", backreference to unset group always fails. '/([ab])(?P=-1)/', // NULL # Regex error: "subpattern name expected", (?P=) expects name not number. # named backreferences '/(?<name>[ab])\g{name}/', // 'xx ab ba xx' '/(?<name>[ab])\g<name>/', // 'xx xx xx xx' # unexpected behavior, backreference matches both 'a' and 'b'. "/(?<name>[ab])\g'name'/", // 'xx xx xx xx' # unexpected behavior, backreference matches both 'a' and 'b'. '/(?<name>[ab])\k{name}/', // 'xx ab ba xx' '/(?<name>[ab])\k<name>/', // 'xx ab ba xx' "/(?<name>[ab])\k'name'/", // 'xx ab ba xx' '/(?<name>[ab])(?P=name)/', // 'xx ab ba xx' ]; foreach ($patterns as $pat) echo " '$pat',\t// " . var_export(@preg_replace($pat, 'xx', 'aa ab ba bb'), 1) . PHP_EOL; ?> ---- Server IP: 45.112.84.4 Probable Submitter: 45.91.159.161 (proxied: 2001:4c4d:2c01:3200:dab2:4c0e:9d8a:4491) ---- Manual Page -- https://php.net/manual/en/regexp.reference.back-references.php Edit -- https://main.php.net/note/edit/127718 Del: integrated -- https://main.php.net/note/delete/127718/integrated Del: useless -- https://main.php.net/note/delete/127718/useless Del: bad code -- https://main.php.net/note/delete/127718/bad+code Del: spam -- https://main.php.net/note/delete/127718/spam Del: non-english -- https://main.php.net/note/delete/127718/non-english Del: in docs -- https://main.php.net/note/delete/127718/in+docs Del: other reasons-- https://main.php.net/note/delete/127718 Reject -- https://main.php.net/note/reject/127718 Search -- https://main.php.net/manage/user-notes.php

« previous php.notes (#219668) next »