Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why is (?!^) equivalent to (?<!^)?

Tags:

regex

A little while back I answered this question on SO, but I still haven't figured out why my answer worked.

For some reason, a negative lookahead for the start of a string behaves the same as a negative lookbehind.

For example, in PHP

preg_replace("/(?!^)12/", "ab", "12345");   // 12345
preg_replace("/(?<!^)12/", "ab", "12345");  // 12345
preg_replace("/(?!1)23/", "ab", "12345");   // 1ab45
preg_replace("/(?<!1)23/", "ab", "12345");  // 12345

I know it's not the most useful question ever asked, but this has been nagging me for a couple of weeks.

like image 541
Andreas Jansson Avatar asked Jul 04 '11 22:07

Andreas Jansson


Video Answer


1 Answers

The caret is a zero-width assertion. In fact lookaheads and lookbehinds are zero-width as well. Therefore, in this case it doesn't matter if you're looking ahead or behind, you're still looking at the same character position.

This is explained pretty well in this article.

like image 120
Steve Wortham Avatar answered Oct 01 '22 17:10

Steve Wortham