1

Is there function which work as:

var regex=/\s*(\w+)/;
var s="abc def ";
var m1=regex.exec(s,0); // -> matches "abc"
var m2=regex.exec(s,3); // -> matches "def"

I know the alternative is:

var regex=/\s*(\w+)/;
var s="abc def ";
var m1=regex.exec(s); // -> matches "abc"
var m2=regex.exec(s.substring(3)); // -> matches " def"

But I worry about that if s is very long and s.substring is called many times, some implementation may work in bad efficiency in which copy long strings many times.

3
  • 2
    You could put .{3} at the beginning of the regex. Commented Sep 10, 2012 at 14:51
  • I assume you know that in this case you can just fire \w+ and then walk each individual match? I'm guessing this is a reduction of your actual scenario, though... Commented Sep 10, 2012 at 14:51
  • How about profiling your code? Or looking at the implementation of a JavaScript virtual machine? Strings in JavaScript are immutable, so a good implementation would share the space for the characters and not copy them. So yeah, substring makes a new object, but does not necessarily copy the character data. The length of your string may well be irrelevant. At any rate, to ensure you don't have an X-Y problem here, consider using the g flag, since you are probably trying to find words over and over again, right? Commented Sep 10, 2012 at 15:03

2 Answers 2

4

Yes, you can make exec start at a particular index if the regex has the g global modifier.

var regex=/\s*(\w+)/g; // give it the "g" modifier

regex.lastIndex = 3;   // set the .lastIndex property to the starting index

var s="abc def ";

var m2=regex.exec(s); // -> matches "def"

If your first code example had the g modifier, then it would work as you wrote it, for the very same reason above. With g, it automatically sets the .lastIndex to the index past the end of the last match, so the next call would start there.

So it depends on what you need.

If you don't know how many matches there will be, the common approach would be to run exec in a loop.

var match,
    regex = /\s*(\w+)/g,
    s = "abc def ";

while(match = regex.exec(s)) {
    alert(match);
}

Or as a do-while.

var match,
    regex = /\s*(\w+)/g,
    s = "abc def ";

do {
    match = regex.exec(s);
    if (match)
        alert(match);
} while(match);
Sign up to request clarification or add additional context in comments.

4 Comments

+1 a nice useful answer, reminding people of g, which is probably the way the OP wants to do things. :)
Thanks. This is what I want to do!
@hoge1e3: You're welcome. And I changed my wording just a little because I think I misunderstood at first. You don't need to manually set the .lastIndex if you ultimately want all the matches in the string. You'd just do like your first example, but include g. Or you can run exec in a loop. I'll update with a loop example.
@hoge1e3 If you have a string with words separated by white space, and you want to get an array of all the words without white space, you could use a_string_with_words_separated_with_space.split(/\s+/);
0

I don't think there is any regular expression method that can do this. If you are worried about performance, I would just store the full string and the snipped string so substring is only ever called once:

var regex=/\s*(\w+)/;
var s="abc def ";
var shorts = s.substring(3);
var m1=regex.exec(s); // -> matches "abc"
var m2=regex.exec(shorts); // -> matches " def"

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.