Getting last match from multiple matches

2019-07-27 14:00发布

I am trying to match and get the last occurrence of a pattern in my file using notepad++.

My text:

X12 

Source =asdjkasjd
 file="x/y1.dun"
       "x/y2.dun"
       "x/y3.dun"

asds12

    X22
       p/q/xy.dun
asda=23

source =asdf

    X44
1000
1001
      file="abc.dun"

What I expect using find-and-replace is this:

X12     x/y3.dun
X22     p/q/xy.dun
X44     abc.dun

What I have tried so far:

(X\d{2}).*?([^"\s]+dun)((?!X\d{2}).)*

replace with:

$1\t\t$2\n

But it returns me this:

X12     x/y1.dun    //Which is the first match
X22     p/q/xy.dun
X44     abc.dun

How do I get the last match inside a match? I am looking for a general way for getting the last match.

1条回答
2楼-- · 2019-07-27 14:41

You may match and capture what you need to keep and just match what you do not need, and only replace with text when a capture group is matched:

Find What: (?s)\b(X\d{2})(?:(?!X\d{2}).)*["\s]([^"\s]+\.dun)|(?:(?!X\d{2}).)*
Replace With: (?{1}$1\t\t$2\n)

See the regex pattern demo.

Details:

  • (?s) - a DOTALL modifier (you may remove it and check the . matches newline option)
  • \b - a leading word boundary to match X at the start of a word
  • (X\d{2}) - Group 1 capturing a X (note that Match Case must be turned on if you do not want to match a lowercase x) and any two digits
  • (?:(?!X\d{2}).)* - a tempered greedy token matching any char, zero or more repetitions, that is not followed with X and any two digits. Since it is greedy, it will make it up to the location where the next character starts the forbidden sequence and will backtrack to the last "dun" required by the subsequent subpattern.
  • ["\s] - a whitespace or a double quote
  • ([^"\s]+\.dun) - Group 2 capturing one or more chars other than whitespace and double quote, then a dot and a dun substring
  • | - or
  • (?:(?!X\d{2}).)* - the same tempered greedy token as above.

Replacement details:

  • (?{1} - if Group 1 matched....
    • $1\t\t$2\n - replace with the first group value, two tabs, the second group value and a newline
  • ) - else replace with an empty string.

enter image description here

查看更多
登录 后发表回答