Reputation: 6200
Assume a regex that should test true for any string containing the substring hello
, followed by any string that does not begin with !
or several of !
.
Some examples for clarity:
var regExp = /someExpression/;
regExp.test("hello"); // → true
regExp.test("hello!"); // → false
regExp.test("hello!!"); // → false
regExp.test("hello!sdkfjhsdfjkh"); // → false
regExp.test("hellos!dkfjhsdfjkh"); // → true
regExp.test("hello-!"); // → true
regExp.test("hello w34~342`!!"); // → true
I have tried several approaches, here's my best:
var regExp = /.*hello[^!].*/;
This will work well on all cases I can come up with but one: "hello"
.
In this case, [^!]
expects a character.
How can I improve this regex so it tests true for this case as well?
Any kind of help is appreciated.
Edit - bonus points:
The same for hello
preceded by a !
, so that hello
is accepted, but !hello
is not.
Upvotes: 3
Views: 336
Reputation: 89557
Use a simple alternation with the end of the string:
/hello([^!]|$)/.test(str);
Upvotes: 0
Reputation: 626896
You need to use a negative look-ahead rather than a negated character class (that still matches, consumes characters):
var regExp = /.*hello(?!!).*/;
See regex demo
See more details at regular-expressions.info:
Negative lookahead is indispensable if you want to match something not followed by something else. When explaining character classes, this tutorial explained why you cannot use a negated character class to match a
q
not followed by au
. Negative lookahead provides the solution:q(?!u)
. The negative lookahead construct is the pair of parentheses, with the opening parenthesis followed by a question mark and an exclamation point.
EDIT:
Since JS regex engine does not support look-behind, you need to match (^|[^!])hello
(where (^|[^!])
matches either start of string or a symbol other than !
) and then do whatever you need to do with it using JS string methods.
Upvotes: 3
Reputation: 3778
With just those cases, negating /hello!/
works just fine:
var regExp = /hello!/;
!regExp.test("hello"); // → true
!regExp.test("hello!"); // → false
!regExp.test("hello!!"); // → false
!regExp.test("hello-!"); // → true
!regExp.test("hello w34~342`!!"); // → true
See: https://regex101.com/r/xI1mG0/1
Upvotes: 1