Some time ago, I encountered some pits in the regular global matching mode. I summarized them here for reference.

What is global matching

If we want to match the target string multiple times, we can use /… /g or create new RegExp(… , ‘g’) matches globally, such that the global property of the regular expression will be true

let reg = /test/g;
reg.global // true
Copy the code

The other global regular expression attribute, lastIndex, represents the position of the first character after the result of the last match to the text, which was found by the methods regexp.prototype.exec () and regexp.prototype.test (), They all take the location indicated by the lastIndex attribute as the starting point for the next retrieval. This allows you to iterate over all the matching text in a string by calling both methods repeatedly. The lastIndex property is readable and writable and can be set as soon as the next search for the target string begins. When the methods regexp.prototype.exec () or regexp.prototype.test () find no more text to match, they automatically reset the lastIndex property to 0.

Regexp.prototype.test () : Checks if a match exists

For non-global regular expressions, test() only checks for the existence of a certain target string. The result is the same multiple times, for example:

let reg = /test/;
let str = '_test_test';
reg.test(str) // true
reg.test(str) // true
Copy the code

When the global flag /g is set, the test() method will return true whenever there is a match in the string, and the lastIndex property will be set to the first character after the last successful match, and the next match will start at the position indicated by lastIndex. Return false on unsuccessful matches and reset the value of the lastIndex property to 0.

let reg = /test/g;
let str = '_test_test';

reg.test(str) // true
reg.lastIndex // 5

reg.test(str) // true
reg.lastIndex // 10

reg.test(str) // false
reg.lastIndex // 0
Copy the code

Regexp.prototype.exec () : Captures the specified string

If the global entry /g is not set, the method always returns the first match:

let reg = /test/;
let str = '_test_test';

reg.exec(str) // ["test", index: 1, input: "_test_test", groups: undefined]
reg.lastIndex // 0

reg.test(str) // ["test", index: 1, input: "_test_test", groups: undefined]
reg.lastIndex // 0
Copy the code

When a global match occurs, this method returns one match at a time, until null is returned when there are no matches:

let reg = /test/g;
let str = '_test_test';

reg.exec(str) // ["test", index: 1, input: "_test_test", groups: undefined]
reg.lastIndex // 5

reg.test(str) // ["test", index: 6, input: "_test_test", groups: undefined]
reg.lastIndex // 10

reg.test(str) // null
reg.lastIndex // 0
Copy the code

String.prototype.search() : finds the matching position

This method ignores the global Settings item and simply returns the location of the first match:

let regex = /test/;
let str = '_test_test'; str.search(regex); / / 1let regex = /test/g;
let str = '_test_test'; regex.lastIndex; // 0 str.search(regex); // 1 regex.lastIndex; // 0, because the method ignores global SettingsCopy the code

String.prototype.match() : Matches one or more regular expressions

If it is not a global match, the first match is returned and lastIndex is ignored:

let regex = /test/;
let str = '_test_test'; str.match(regex); / / /"test", index: 1, input: "_test_test"] regex.lastIndex // 0 str.match(regex); / / /"test", index: 1, input: "_test_test"]
regex.lastIndex   // 0
Copy the code

For global matches, this method returns all matches and ignores lastIndex:

let regex = /test/g;
let str = '_test_test'; str.match(regex); / / /"test"."test"] regex.lastIndex // 0 str.match(regex); / / /"test"."test"] regex.lastIndex // 0 str.match(regex); / / /"test"."test"]
regex.lastIndex   // 0
Copy the code

String.prototype.replace() : Replaces substrings that match regular expressions

If no global match is set, the position of the first match is replaced; If global matching is set, all matching positions are replaced:

// Not a global match'_test_test'.replace(/test/, 'r');  // '_r_test'// Global matching'_test_test'.replace(/test/g, 'r'); // '_r_r'
Copy the code

Reference link: bubkoo.com/2014/03/19/…