7

Sometimes, I want to test is my regex correct.

How can I do reverse regex match from stdin?

F.e. I can match a string with provided regex, like:

grep "\(foo\)-bar"
foo
bar
foo-bar
foo-bar #Match found

What I would like to do, is the opposite, something like this:

$ grep "This is one string"
\(This\) #Will send "This" to stdout
This?.*  #Will send full match

Is this somehow possible without much scripting?

  • escaping the parentheses implies grouping in sed; otherwise, awk and grep will uselessly group "This" and should instead output the entire line (in your example), not just "This". can you clarify what kind of behavior you're after? – Jeff Schaller May 31 '17 at 0:30
5

You can use - as the "file" to search, which will use standard input as the "haystack" to search for matching "needles" in:

$ grep -oE '[aeiou]+' -
This is a test  < input
i               > output
i               > output
a               > output
e               > output
whaaaat?        < input
aaaa            > output

Use Ctrl-D to send EOF and end the stream.

I don't believe, though, that you can do the same to use standard input for the -f switch which reads a list of patterns from a file. However, if you have a lot of patterns to text on one corpus, you can:

grep -f needle-patterns haystack.txt

where needle-patterns is a plaintext file with one regular expression per line.

  • Yes, exactly what I need :) – fugitive May 30 '17 at 23:50
  • 1
    @fugitive But all, that it doing is getting input from stdin, the rest is the same. It doesn't take regex pattern, like This?.*, how you were asking. – MiniMax May 31 '17 at 0:10
  • 1
    Which is where the alternative of a list of patterns to test comes into play. Sadly, you can't grep -f - haystack, it will complain that the file - does not exist. – DopeGhoti May 31 '17 at 0:17
  • On the contrary: with GNU grep, you can use grep -f - haystack, but it's not very useful anyway for OP's purpose because it will wait until you press Ctrl-D to signal end of input, and then for each line in "haystack" will only either print it or not print it—it won't print it multiple times if it matches multiple patterns, and it won't print anything until you finish typing all your patterns. – Wildcard May 31 '17 at 0:23
  • 2
    @fugitive This may be what you want, but not at all what you described. You were asking to interactively input patterns to match a given string, but this searches for a pattern in interactively input string, like what you already had. The solution by Wildcard is the one that answered your question! – Philippos May 31 '17 at 5:52
7

Define the following function in your shell (you can just type it in, or put it in your ~/.bashrc):

testregex() {
  [ "$#" -eq 1 ] || return 1
  while IFS= read -r line; do
    printf '%s\n' "$1" | grep -Eoe "$line"
  done
}

Then you can test a regex as follows:

$ testregex 'This is a line'
This            <--input
This            <--output
This?.*         <--input
This is a line  <--output
slkdjflksdj     <--input with no output (no match)
s.*             <--input
s is a line     <--output
$               <--I pressed Ctrl-D to end the test
  • 3
    This is a great solution! Neat and simple. You could also easily expand it to allow a second argument and, if present, pass that argument to grep. That way, you can play with BRE, ERE, PCRE and whatever else your grep has flags for. – terdon May 31 '17 at 0:36
  • Great one as well. – fugitive May 31 '17 at 10:09
  • I would like to add pattern buffering and may be sed|awk|grep parameter, then it will be quite useful utility for pattern picking. Like, run testregex -program=sed 'This is a line', then give it different pattern variants, fetching previos|next pattern by arrow keys and edit it - similar to bash command history. Because it is not very handy retype whole pattern every time. – MiniMax May 31 '17 at 12:29
  • It seems, for that, it need be implement entire readline library - for pattern editing and so on :) – MiniMax May 31 '17 at 12:45

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.