1. Determine if the document is an XML document
var isxml = function (elem) {
var documentelement = Elem && (elem.ownerdocument | | elem). documentelement;
Return documentelement? Documentelement.nodename!== "HTML": false;
}
To understand the above code, the two differences need to be understood first:
Ownerdocument returns the root node of an element document object (that is, the documents object)
And documentelement returns the document root node. (The HTML document is the Html,xml document is the outermost node element)
Therefore, if the elements in the incoming function belong to an HTML document, then DocumentElement = document.documentelement = html, so the HTML element's nodename = = "html" (will default to uppercase).
If the incoming element is an XML document, then documentelement = Document.documentelement = The outermost node element, which cannot be an HTML (HTML document), so it returns true.
This is the method in jquery, but this is not rigorous: because the root node of XML may be an HTML tag. (But who's so bored to create XML like that?)
There is a more rigorous approach:
var isxml = function (doc) {
//xml A document creates an element, it passes in lowercase letters, and nodename is lowercase when it is taken. The HTML document, whether in lowercase or uppercase, will be capitalized when it is nodename
Return Doc.createelement ("P"). NodeName!== doc.createelement ("P"). NodeName;
}
2. Determine the relationship of two nodes
Results returned by Nodea.comparedocumentposition (NodeB)://Standard browser support, low version browser not supported
0: Element Consistent
1: The node is in a different document (or has a node outside the document)
2: Node B before Node A
4: Node A before node B
8: Node B contains Node A
16: Node A contains node B
32: Private use of the browser
Of course, the position relationship of the two elements may satisfy both cases, such as: A contains B, and a is in front of B, then returns 16+4=20.
In order to be compatible with the low version of the browser, you can use the private property of IE sourceindex processing, sourceindex will be based on the position of the element from top to bottom, from left to right, add 1, such as the HTML tag sourceindex 0,head labeled 1,body label is 2, The first child element of head is 3 ..., and if the element is not in the DOM tree, it returns-1.
3. Sorting nodes
In order for the selector engine to search for the same result set as the native API results, we need to have the element nodes sorted in the order in which they appear in the DOM tree.
(1) in IE and earlier versions of opera, Sourceindex can be used for sorting. Standard browsers can be sorted using comparedocumentposition judgments.
(2) The Range object of the standard browser has a compareboundarypoints method, which can quickly get the order of two elements. To be compatible with older browsers and XML documents, you can use DOM APIs such as NextSibling. (The so-called "Range"
refers to any piece of content in an HTML document.) Range
the starting point and end point position can be arbitrary, even the starting and ending points can be the same (i.e., empty Range
). The most common Range
is the user Text selection range (selection). When the user selects a piece of text on the page, you can convert the selection to a Range
. Of course, you can also use the program definition directly Range
. )
(3) After we have chosen the selector engine, we use document.getElementsByTagName ("*") to get all the element nodes, and they must be well sequenced. We add a custom property that is similar to sourceindex for them in turn, and the value is its index value. Then go to match the selector engine and choose the result, and you can sort it out.
Here's a tip for you: Array native sort method, each browser uses a different sort algorithm. But when it comes to a comparison function, it takes a lot more time than that, regardless of which sort algorithm is used internally.
Here's a look at the recurring interview questions: Sort the element nodes. We can attach an element node to an array of string objects, such as: [{"0": Element 1},{"1": Element 2},{"2": Element 3}], reverse the array, and then take the elements according to the order of the array, and the element nodes are reversed.
4. Cutting device
The cutter is to cut the user's selector, this step is like the compilation principle of lexical analysis, split out useful symbols out.
For example: for the ". Td1,div a,body" Selector string, we must use the regular to break it into the following array: [". TD1", ",", "div", "", "*", ",", "body").
You can then create and filter elements based on each item in the array. Finally go to reorder, get the element that the user wants.
This is mainly used for regular expressions to handle strings, requiring a strong regular expression base, suitable for in-depth study of regular people.
Come on!
Lesson 11th: General functions involved in the selector engine