I'd like to use grep
with a PCRE expression that contains the <
character. Bash thinks I want to redirect, but I don't want to. How can I escape <
?
I was able to do it with a backslash:
25 % grep \< xmospos.c
#include <stdio.h>
#include <stdlib.h>
#include <getopt.h>
#include <X11/Xlib.h>
A quoted less-than, and a quoted, backslashed less than both gave goofy answers.
-
5
-
I still need to learn, e.g. how that exactly works with escaping:
grep -oP '(?< )(.*)$'
does not work with single quotes for example. Tried it at first. – hakre Jul 26 '11 at 8:50 -
@hakre There seems to be a syntax error in your regexp. Did you mean
(?<! )(.*)$
or(?<= )(.*)$
? – Gilles 'SO- stop being evil' Jul 26 '11 at 22:18
Two simple rules:
- A backslash
\C
escapes the next character, whatever it is, other than a newline. - Single quotes
'text'
escape any character between them, including a backslash, but not including a single quote (since it marks the end of the quoted text).
Thus:
grep -P '<html>' myfile
grep -P \<html\> myfile
grep -P '(?<!<)html' myfile
grep -P \(\?\<\!\<\) myfile
If you need to pass an argument that contains single quotes, you can use '\''
to “escape” a single quote inside single quotes. Technically, what this does is end the first literal text, then put a literal '
in the same word, then more literal text still in the same word.
grep '^D'\''oh!' myfile
The rest of the quoting rules (summarized):
- You need to quote the following characters at least some of the times: whitespace and
!"#$&'()*;<>?[\]^`{|}~
(in other words, the following characters are safe: letters, digits,%+,-./:=@_
and non-ASCII characters). - Between double quotes, all characters are used literally except
"$\`
and (in shells with history enabled)!
. A backslash between double quotes will appear in the string unless it precedes one of the non-literal characters.
These rules are for bash and other Bourne-style shells (such as ash and ksh). They apply to zsh as well (except that =
after whitespace may need quoting). The rules in csh/tcsh and in Fish are different.