slayer
slayer

Reputation: 445

Return only one group with OR condition in Regex

I have to write a Regex to fetch Email Address from a sentence. I want it to be returned with Group 1 only.

Regex:

\[mailto:(.+)\]|<(.+@.+\..+)>

Input String:

Hello my Email Address is <[email protected]> - Return [email protected] as Group1.
Hello my Email Address is [mailto: [email protected]] - Return [email protected] as Group2.

I want if any of the string matches then it should be returned in Group1.

Is there any way to do this?

Upvotes: 1

Views: 3144

Answers (2)

The fourth bird
The fourth bird

Reputation: 163577

You could first match either < and assert that it ends with ..> or match [mailto: and assert that it ends with ]

To prevent unnecessary backtracking and prevent over matching, you can use a negated character class, denoted by [^

(?:<(?=[^<>]*>)|\[mailto:\s*(?=[^][]*]))([^\s@]+@[^\s@]+\.\w{2,})

The pattern matches:

  • (?: Non capture group for the alternatives
    • <(?=[^<>]*>) Match < and assert ...> without any occurrence of < or > in between
    • | Or
    • \[mailto:\s* match [mailto: followed by optional whitespace chars
    • (?=[^][]*]) Postive lookahead, assert matching optional chars other than [ or ] and match ]
  • ) Close the non capture group
  • ( Capture group 1
    • [^\s@]+ Match 1+ chars other than @ or a whitespace char
    • @ Match the @
    • [^\s@]+\.\w{2,} Match 1+ chars other than @ or a whitespace char followed by a dot and 2 or more word chars (you can make the TLD as specific as you want)
  • ) Close group 1

See a regex demo

Upvotes: 0

Paolo
Paolo

Reputation: 26220

You may use regular expression:

(?=\S+@)([^<\s]+@.*(?=[>\]]))
  • (?=\S+@) Positive lookahead, assert that what follows is any non-whitespace characters followed by @.
  • ([^<\s]+@.*(?=[>\]])) Capture group. Capture any non-whitespace, non ^ character followed by @, and anything up to either a ] or > character.

You can test the regular expression here.

Upvotes: 1

Related Questions