document.evaluate的详细⽤法
URL:hi.baidu/xiaojipai/blog/item/5a772697eb1ebd6d54fb965f.html
URL:/en/docs/Introduction_to_using_XPath_in_JavaScript
使⽤ Greasemonkey 时会遇到的功能最为强⼤的⼀个⼯具就是 evaluate 函数。通过使⽤XPath这种查询语⾔,它可以⽤来寻页⾯中的元素,属性和⽂本。
举个例⼦来说,如果您想获得某个页⾯上的全部链接。您也许会想到使⽤ElementsByTagName('a');但是如果您还要继续检查是否每个链接都具有href属性,因为<a>还可以⽤来作为锚名称使⽤,这时,您需要使⽤Firefox内建的XPath ⽀持去获取全部具有href属性的<a>元素。
例⼦: 获取页⾯上的全部链接
var allLinks, thisLink;
allLinks = document.evaluate(
'//a[@href]',
document,
null,
XPathResult.UNORDERED_NODE_SNAPSHOT_TYPE,
null);
for (var i = 0; i < allLinks.snapshotLength; i++) {
thisLink = allLinks.snapshotItem(i);
// do something with thisLink
}
这⾥,document.evaluate 是关键的部分。 它把 XPath 查询语句作为⼀个字符串,其它的参数稍后再做解释。 这条 XPath 查询语句可以到全部具有href属性的<a>元素,并将它们按照随机的顺序依次返回。(这就是说,第⼀个被返回的元素并⼀定也是页⾯上的第⼀个这样的元素。) 随后,您就可以⽤ allLinks.snapshotItem(i) 函数访问每⼀个元素。
XPath表达式所能做到的甚⾄会使您惊讶。请看下⾯这个例⼦,它获取了全部具有title属性的元素。
例⼦: 获取全部具有title属性的元素
var allElements, thisElement;
allElements = document.evaluate(
'//*[@title]',
document,
null,
XPathResult.UNORDERED_NODE_SNAPSHOT_TYPE,
null);
for (var i = 0; i < allElements.snapshotLength; i++) {
thisElement = allElements.snapshotItem(i);
switch (UpperCase()) {
case 'A':
// this is a link, do something
break;
case 'IMG':
// this is an image, do something else
break;
default:
// do something with other kinds of HTML elements
}
}
如果您已经引⽤了某个元素(例如上⾯的 thisElement),您就可以⽤ deName 来替代它所对应的在 HTML 页⾯中的标签名称。如果被访问的这个页⾯是以 text/html 的⽅式被服务器执⾏, 那么标签名称总是⽤⼤写⼦母返回,不论它在原始页⾯是如何定义的。 如果页⾯是 application/xhtml+xml ⽅式的, 那么标签名称就会以⼩写⼦母返回。 不论哪种情况,我总是⽤
这是另外⼀个 XPath 查询,它返回了 div 中的⼀个特殊的类。
例⼦: 获取 div 中的 sponsoredlink 类
var allDivs, thisDiv;
allDivs = document.evaluate(
"//div[@class='sponsoredlink']",
document,
null,
XPathResult.UNORDERED_NODE_SNAPSHOT_TYPE,
null);
for (var i = 0; i < allDivs.snapshotLength; i++) {
thisDiv = allDivs.snapshotItem(i);
// do something with thisDiv
}
注意我在 XPath 查询语句外使⽤了双引号,这样在语句内部就可以使⽤单引号。
在 document.evaluate 函数中有很多参数。第⼆个参数 (在前两个例⼦中都是docoment) 可以是⼀个元素, XPath 查询只返回包含在这个元素内的元素。所以,如果您已经引⽤了⼀个元素(⽐如, 通过 ElementById 或者 通过
第三个参数是对⼀个叫做 namespace resolver 函数的引⽤, 它只有在⼯作在 application/xhtml+xml 类型的页⾯上的⽤户脚本中是有效的。即使您对它不是很了解也没有关系,因为那种类型的页⾯不是很多,您可能⼀次也遇不到。 如果您很想知道它是如何使⽤的,请参考Mozilla XPath documentation (www-jcsu.jesus.cam.ac.uk/~jg307/mozilla/xpath-tutorial.html),那⾥解释了它的⽤法。
第四个参数是结果的返回⽅式。在前⾯的两个例⼦中都使⽤了 XPathResult.UNORDERED_NODE_SNAPSHOT_TYPE, 它将结果以随机的⽅式返回。我使⽤的⼏乎全部都是这种⽅式,但是,出于某种原因,您想让结果以它们在页⾯上出现的顺序返回,您可以使⽤XPathResult.ORDERED_NODE_SNAPSHOT_TYPE 这种⽅式。 Mozilla XPath documentation (www-
html document是什么jcsu.jesus.cam.ac.uk/~jg307/mozilla/xpath-tutorial.html)还给出了另外的⼀些⽤例。
第五个参数⽤来合并两次 XPath 查询的结果。 在获得第⼀次调⽤ document.evaluate 得到的结果之后,它将两次查询的结果⼀起返回。在前⾯的两个例⼦中,这个参数都⽤了null,这意味着我们只想获得本次查询的结果。
现在您明⽩了吗?XPath 既可以很简单,也可以很难,这取决于您要如何使⽤它。在此我强烈推荐您尽快去阅读 this excellent XPath tutorial (/xxl/XPathTutorial/General/examples.ht
ml),从⽽了解更多的 XPath 语法。⾄于
document.evaluate 函数的其它参数, 我⼏乎从来不使⽤它们。事实上,您可以⾃⼰定义⼀个函数来封装它们。
例⼦: ⾃定义的 xpath 函数
function xpath(query) {
return document.evaluate(query, document, null,
XPathResult.UNORDERED_NODE_SNAPSHOT_TYPE, null);
}
在定义了这个函数之后,您就可以调⽤ xpath('//a[@href]') 来获得某个页⾯上的全部链接, 或者调⽤ xpath('//* [@title]') 来获得具有 title 属性的元素。您仍然需要通过 snapshotItem 函数来访问结果中的每⼀项,这个函数的类型并不是⼀个规则的Javascript数组。
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论