Michael Cheng
Michael Cheng

Reputation: 151

How to select one character in a string in between characters with Regex?

Given this single-line input:

City, Country|[email protected]|john-doe-1234567|https://www.example.com/john-doe-site|john|doe|

I want to know if this is possible to grab the last two | characters - ie the pipes surrounding doe, but without matching doe.

I know the regex code to get all the | with (\n?)\|.

I've tried (?<=[a-z])\|\w+\| and (?<![a-z])\|\w+\|. The positive lookbehind and negative lookbehind both were closest I got but didn't hit the mark... In VSCode, I get something like this:

enter image description here

Currently, can not figure out a way where I get just the last two | characters without also returning a word that comes in-between the |.

Upvotes: 2

Views: 157

Answers (2)

Bohemian
Bohemian

Reputation: 425033

Use a look ahead for the rest of input being 0-n non-pipes then an optional pipe (which includes being nothing - ie will match the last char):

\|(?=[^|]*\|?$)

See live demo.

Regex breakdown:

  • \| a (literal) pipe
  • (?=...) a look ahead, which asserts that what follows matches ...
  • [^|]* any number (including none) of chars not a pipe (note how the pipe char doesn't need escaping when in a character class, as is the case for most chars that would otherwise have special meaning)
  • \|? an optional pipe char
  • $ end of input

Upvotes: 1

Ryszard Czech
Ryszard Czech

Reputation: 18611

Use

\|(?=(?:[^|]*\|)?[^|]*$)

See regex proof.

BREAKDOWN

--------------------------------------------------------------------------------
  \|                       '|'
--------------------------------------------------------------------------------
  (?=                      look ahead to see if there is:
--------------------------------------------------------------------------------
    (?:                      group, but do not capture (optional
                             (matching the most amount possible)):
--------------------------------------------------------------------------------
      [^|]*                    any character except: '|' (0 or more
                               times (matching the most amount
                               possible))
--------------------------------------------------------------------------------
      \|                       '|'
--------------------------------------------------------------------------------
    )?                       end of grouping
--------------------------------------------------------------------------------
    [^|]*                    any character except: '|' (0 or more
                             times (matching the most amount
                             possible))
--------------------------------------------------------------------------------
    $                        before an optional \n, and the end of
                             the string
--------------------------------------------------------------------------------
  )                        end of look-ahead

Upvotes: 0

Related Questions