Differences between Vim Regex, Emacs Regex and PCRE
24 Feb 2020When I first switched over from Vim to Spacemacs, one thing that really caught me off guard was the behavior of /
search under evil-mode
. evil-mode
reproduces the Vim experience so well, it’s easy to forget the underlying Emacs base of it all.
Turns out, both Vim and Emacs have their own regex syntaxes that are slightly different from the one used by PCRE (Perl-Compatible Regular Expressions). vi
(and its predecessor ed
) and emacs
are both older than Perl, so this is to be expected.
I would like to list some of the differences that are likely to be encountered in your day-to-day work. I will also list some resources that you can refer to for more details.
Differences between Emacs Lisp regex and PCRE regex
The following are some common gotchas of Elisp regex:
- You need to escape some additional symbols such as:
- backslash
\
:\\
- alternation
|
:\|
- grouping
(
and)
:\(
and\)
- counting
{
and}
:\{
and\}
- backslash
\s
begins a syntax class. Whitespaces are denoted as\s-
instead of\s
.- Use
[0-9]
or[:digit:]
instead of\d
to denote digits. - Use
\1
,\2
etc. instead of$1
,$2
to refer to the results of capturing parentheses.
For more details, refer to The EmacsWiki and this SO question.
In addition, there is a tool which converts PCRE regex to Emacs regex.
Differences between Vim regex and PCRE regex
This SO answer by J-P summarizes some the common gotchas of Vim regex:
Perl Vim Meaning
---------------------------
x? x\= Match 0 or 1 of x
x+ x\+ Match 1 or more of x
(xyz) \(xyz\) Use brackets to group matches
x{n,m} x\{n,m} Match n to m of x
x*? x\{-} Match 0 or 1 of x, non-greedy
x+? x\{-1,} Match 1 or more of x, non-greedy
\b \< \> Word boundaries
$n \n Backreferences for previously grouped matches
You can also get some additional information via :help perl-patterns
.
There are some ways to change the behavior of Vim regex:
- Use the “very magic regex mode” by prepending the pattern with
\v
. However, note that\b
will still mean “backspace” instead of “word boundaries”. - Manually run
perl
::perldo s/searchme/replaceme/g
. - Use the plugin eregex.vim which performs the conversion automatically and allows you to search using PCRE regex by default.