I think this is a very basic question, but I really can't understand the concept. I have the following regular expression:
var t = '11:59 am';
t.match(/^(\d+)/);
Now, according to my understanding when I print the value I should just get 11 since I am just checking for digits. However, I get 11,11. I have to use 0th element to pick the required value like t.match(/^(\d+)/)[0].
This is because you are using a capture group, (), around the digits. Try replacing this with:
t.match(/^\d+/);
Note: this will still return an array, because that's just what .match() does.
match() always returns an array if there are any matches. Element [0] is the whole match, and element [1] is what is inside the first set of parentheses.
Related
I want to get all the words, except one, from a string using JS regex match function. For example, for a string testhello123worldtestWTF, excluding the word test, the result would be helloworldWTF.
I realize that I have to do it using look-ahead functions, but I can't figiure out how exactly. I came up with the following regex (?!test)[a-zA-Z]+(?=.*test), however, it work only partially.
http://refiddle.com/refiddles/59511c2075622d324c090000
IMHO, I would try to replace the incriminated word with an empty string, no?
Lookarounds seem to be an overkill for it, you can just replace the test with nothing:
var str = 'testhello123worldtestWTF';
var res = str.replace(/test/g, '');
Plugging this into your refiddle produces the results you're looking for:
/(test)/g
It matches all occurrences of the word "test" without picking up unwanted words/letters. You can set this to whatever variable you need to hold these.
WORDS OF CAUTION
Seeing that you have no set delimiters in your inputted string, I must say that you cannot reliably exclude a specific word - to a certain extent.
For example, if you want to exclude test, this might create a problem if the input was protester or rotatestreet. You don't have clear demarcations of what a word is, thus leading you to exclude test when you might not have meant to.
On the other hand, if you just want to ignore the string test regardless, just replace test with an empty string and you are good to go.
So I find this really hard to explain what im doing, but its easy to show in an example.
I have these 2 strings and I need a regular expression that will only return a value for one of them
Ref Numbers: RCPT:02972, VLBL#:7158461 $930.38
2012-10- 01 5558461 abagaa
I need the 5558461 but not the 7158461, so basically a 7 digit number. I was trying to do this where Ref Numbers exists do not return anything, but if it doesn't then return the 7 digit number.
I've tried many different things but I just cannot get what I need. does anyone out there have an idea what needs to be done?
Thanks
Use negative lookahead assertion like below,
^(?!.*Ref).*\b(\d{7})\b
Use the above regex and get the number you want from group index 1.
DEMO
> var s = "Ref Numbers: RCPT:02972, VLBL#:7158461 $930.38\n2012-10- 01 5558461 abagaa"
> console.log(/^(?!.*Ref).*\b(\d{7})\b/m.exec(s)[1]);
5558461
Negative lookahead (?!.*Ref) at the first asserts that the line where the match going to occur won't have the string like Ref
Why does string.match( /(regexp)/ ); with parentheses return the match twice?
For instance: "abcdef".match(/(cd)/);returns two instances of cd: ["cd","cd"]
I've looked in the MDN documentation. It doesn't say anything about returning the match multiple times.
I even looked in the ECMA docs.
There's a workaround by just grabbing the [1] index string.match() but I couldn't find an explanation in the docs.
Let's follow the docs on RegExp.match
If the regular expression does not include the g flag, returns the
same result as RegExp.exec(str).
Ok, go to RegExp.exec
If the match succeeds, the exec method returns an array and updates
properties of the regular expression object. The returned array has
the matched text as the first item, and then one item for each
capturing parenthesis that matched containing the text that was
captured.
Surprisingly, the MDN docs (here's a Wayback snapshot of it right now) are indeed silent on this, but I bet match returns the entire match first, just like RegExp.exec
Here's a test:
"abcdef".match(/(bc).?(e)/)
=> ["bcde", "bc", "e"]
Say I have a string "&something=variable&something_else=var2"
I want to match between &something= and &, so I'll write a regular expression that looks like:
/(&something=).*?(&)/
And the result of .match() will be an array:
["&something=variable&", "&something=", "&"]
I've always solved this by just replacing the start and end elements manually but is there a way to not include them in the match results at all?
You're using the wrong capturing groups. You should be using this:
/&something=(.*?)&/
This means that instead of capturing the stuff you don't want (the delimiters), you capture what you do want (the data).
You can't avoid them showing up in your match results at all, but you can change how they show up and make it more useful for you.
If you change your match pattern to /&something=(.+?)&/ then using your test string of "&something=variable&something_else=var2" the match result array is ["&something=variable&", "variable"]
The first element is always the entire match, but the second one, will be the captured portion from the parentheses, which is much more useful, generally.
I hope this helps.
If you are trying to get variable out of the string, using replace with backreferences will get you what you want:
"&something=variable&something_else=var2".replace(/^.*&something=(.*?)&.*$/, '$1')
gives you
"variable"
I am trying to match a string containing a mix of digits and hyphenated digits, like a crossword answer specification, for example 1,2-2 or 1-1,3,4,2-2
/,?(([1-9]-[1-9])|([1-9]))/g is what I've come up to match the string
value = value.replace(/,?(([1-9]-[1-9])|([1-9]))/g, '');
replaces ok, and I've checked it out in an online tester.
What I really need is to negate this, so I can use it on a keyup event, examine the contents of a textarea and remove characters that don't fit, so it only allows through characters as in the example.
I've tried ^ where expected, but this it's not doing what I expect, how should I negate the regex so I remove everything that doesn't match?
If there is a better way of doing this I'm open to suggestions too.
var value = 'hello,1,2,3,4-6,1-1,3,test,4,2-2';
var pattern = /,?(([1-9]-[1-9])|([1-9]))/g;
value.replace(pattern, ''); // "hello,test"
You can use String#match. With /g flag, it returns an array of all the matches, then you can use Array#join to join them.
The problem is that String#match returns null when there is no match, so you have to handle that case and use an empty array so that it can join:
(value.match(pattern) || []).join(''); // ",1,2,3,4-6,1-1,3,4,2-2"
Note: It may better to check them on onblur rather than onkeyup. Messing with the text that the user is currently typing will make it annoying. Better to wait for the user to finish typing.
Didn't test it in JS, but this should return the valid string beginning from the left and as long as valid values are encountered (note that I used \d - if you'd like 1-9 only, then use your brackets).
(?:\d(?:-\d)?,)*\d(?:-\d)?
E.g. matching this regular expression with the string "0-1,1,2,3,4-4,2,,1,3--4" will return "0-1,1,2,3,4-4,2" as the first match.