Hal_9100
Hal_9100

Reputation: 951

javascript regex check character before match but don't include it in result

I'm trying to implement the two following rules in a single regex:

If a number is preceeded by :

I tried: [^@\d,\w]\d+ and (?:[^@\d,\w])\d+

Which solve the first rule, but fail to solve the second one, as it includes the operator in the result.

I understand why it doesn't work as intended ; the [^@\d\w] part explicitly says to not match numbers preceeded by a @ or a word character, so it implicitly says to include anything else in the result. Problem is I still have no idea how to solve this.

Is there any way to implement the two rules in a single regex ?

Input string:

@121 //do not match
+39  //match but don't include the + sign in result
s21  //do not match
89   //match
(98  //match but don't include the ( in result
/4   //match but don't include the / operator in result

Expected result:

39 //operator removed
89  
98 //( removed
4  //operator removed

Upvotes: 0

Views: 968

Answers (2)

MinusFour
MinusFour

Reputation: 14423

There's a finished proposal for negative lookbehind which I think it's what you are looking for:

let arr =
['@121', //do not match
'+39', //match but don't include the + sign in result
's21',  //do not match
'89',   //match
'(98',  //match but don't include the ( in result
'/4'   //match but don't include the / operator in result
];

console.log(arr.map(v => v.match(/(?<![@\w])\d+/)));

It's a bleeding edge feature however (works on chromium 62+ i think).

Upvotes: 1

ctwheels
ctwheels

Reputation: 22817

Capture the result you're seeking as the snippet below suggests.

See regex in use here

^[^@\w]?(\d+)
  • ^ Assert position at the start of the line
  • [^@\w]? Optionally match any character except @ or a word character
  • (\d+) Capture one or more digits into capture group 1

var a = ["@121", "+39", "s21", "89", "(98", "/4"]
var r = /^[^@\w]?(\d+)/

a.forEach(function(s){
  var m = s.match(r)
  if(m != null) console.log(m[1])
})

Upvotes: 2

Related Questions