This article mainly introduces the jQuery selector source code (4): Expr of the tokenize method. preFilter. This article explains the Expr of the tokenize method in detail. the source code of the preFilter implementation. For more information, see Expr. preFilter is a preprocessing method for ATTR, CHILD, and PSEUDO selectors in the tokenize method. The details are as follows:
Expr. preFilter: {"ATTR": function (match) {/** to complete the following tasks: * 1. attribute name decoding * 2. attribute value decoding * 3. if the judgment character is ~ =, A space is added on both sides of the property value * 4. The final mtach object ** match [1] is returned to indicate the property name, * match [1]. replace (runescape, funescape): decodes the hexadecimal number in the attribute name into * single-byte unicode character or double-byte unicode character (Chinese or other text that requires two bytes) * for a detailed description of the regular expression, refer to my "jQuery selector regular expression" article */match [1] = match [1]. replace (runescape, funescape);/** decodes attribute values * match [4]: attribute values placed in single or double quotation marks * match [5]: indicates the attribute value without quotation marks */match [3] = (match [4] | match [5] | ""). replace (runescape, funescape );/**~ = Indicates word matching. in W3C, the definition of a word is a blank separator for different words. * Therefore, after spaces are added on both sides of match [3], indexOf can be used, correctly identifies whether the word exists */if (match [2] = "~ = ") {Match [3] =" "+ match [3] +" ";}/** returns the first four useful element results */return match. slice (0, 4) ;}, "CHILD": function (match) {/** to complete the following tasks: * 1. convert the characters before child and of-type in the command to lowercase characters * 2. check the data validity in brackets for the selector starting with nth * 3. match [4] and match [5] respectively store x and B in xn + B, x and B can be negative * 4. return the final match object ** match [1] :( only | first | last | nth-last) */match [1] = match [1]. toLowerCase ();/** four types of brackets, nth-child, nth-of-type, nth-last-child, and nth-last-of-type, must be set. Set valid data * while other parameters cannot contain any data */if (match [1]. slice (0, 3) = "nth") {/** if no valid parameter exists in the selector brackets, an exception is thrown * Example: If the selector is nth or nth (abc) it is an invalid selector */if (! Match [3]) {Sizzle. error (match [0]);}/** the following uses nth-child () as an example to describe the syntax, to better understand the role of the following code * nth-child allows the following usage methods: *: nth-child (even) *: nth-child (odd )*: nth-child (3n) *: nth-child (+ 2n + 1) *: nth-child (2n-1) * In the following code, match [4] and match [5] on the left of the assigned number are used to record the values before and after n in the brackets, including the plus and minus signs. *: for nth-child (even) and: nth-child (odd), match [4] is null, * therefore, 2 * is returned (match [3] === "even" | match [3] === "odd ") * because true = 1, false = 0 in js, (match [3] =" Even "| match [3] ===" odd ") equal to 1 * therefore, 2 * (match [3] === "even" | match [3] === "odd ") the calculation result is 2 ** + on the right side of the equal sign to force type conversion, convert the subsequent string to the numeric type */match [4] = + (match [4]? Match [5] + (match [6] | 1 ): 2 * (match [3] === "even" | match [3] === "odd ")); match [5] = + (match [7] + match [8]) | match [3] = "odd ");} else if (match [3]) {/** if other CHILD type selectors without nth headers have brackets, an exception is thrown. * jQuery is not determined strictly according to W3C rules, because it allows this form of: first-child () to exist * that is, for jQuery: first-child () is equivalent to: first-child, which is a valid selector */Sizzle. error (match [0]);} return match;}, "PSEUDO": function (match) {/** to complete the following tasks: * 1. obtain the value enclosed by quotation marks in a pseudo class. * 2. for values enclosed by non-quotation marks, if pseudo-class nesting exists, the actual end position of the current pseudo-class will be further resolved and determined, * obtain the complete string and value of the current pseudo-class * 3. return the first three copies of the match. ** Unquoted indicates the value enclosed by non-quotation marks in the brackets. * For example, in eq (2), unquoted = 2 */var excess, unquoted =! Match [5] & match [2];/** because the matching regular expression of pseudo and child has an intersection, ignore the child part */if (matchExpr ["CHILD"]. test (match [0]) {return null;}/** if the values in the brackets are enclosed by quotation marks (match [3, * The value except the quotation marks (match [4]) is assigned to match [2]. * Match [3] indicates quotation marks. */If (match [3] & match [4]! = Undefined) {match [2] = match [4];} else if (unquoted/** rpseudo. test (unquoted): used to test whether unquoted contains a pseudo class. * if it contains a pseudo class, it indicates that there may be a possibility of pseudo-class nesting. further unquoted parsing is required. * For example :: not (: eq (3) */& rpseudo. test (unquoted) &/** obtains the position of the last character continuously valid in unquoted */(excess = tokenize (unquoted, true) &/** unquoted. indexOf (")", unquoted. length-excess) * find the ")" position after the last character position of the continuously valid selector obtained previously, * usually after the current position. * Subtract unquoted. length is used to obtain the final position of the valid and complete pseudo-class string in match [0]. * Note that excess is a negative value. **/(excess = unquoted. indexOf (")", unquoted. length-excess)-unquoted. length) {// obtain valid full pseudo-class match [0] and data in pseudo-class brackets match [2] match [0] = match [0]. slice (0, excess); match [2] = unquoted. slice (0, excess);} // return the copy of the first three elements of match return match. slice (0, 3 );}}