Различные результаты при выборе элементов HTML с помощью XPath в Firefox и Internet Explorer

Я пытаюсь выбрать конкретный элемент HTML в документе, для firefox я просто использую:

xpathobj = document.evaluate(xpath, document, null,
               XPathResult.FIRST_ORDERED_NODE_TYPE, null);

который отлично работает. Однако, когда я пробую эквивалент IE:

xmlDoc=new ActiveXObject("Microsoft.XMLDOM");
xmlDoc.async=false;
xmlDoc.load(document);
xmlDoc.setProperty("SelectionLanguage", "XPath");
xpathobj = xmlDoc.selectNodes(xpath);

Я не получил никакого возвращенного объекта. Итак, мой вопрос: есть ли простой способ использовать XPath для доступа к элементу, который я хочу в IE? XPath, который я использую, выглядит как

/HTML/BODY/DIV[9]/DIV[2]
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
В настоящее время производительность загрузки веб-сайта имеет решающее значение не только для удобства пользователей, но и для ранжирования в...
Безумие обратных вызовов в javascript [JS]
Безумие обратных вызовов в javascript [JS]
Здравствуйте! Юный падаван 🚀. Присоединяйся ко мне, чтобы разобраться в одной из самых запутанных концепций, когда вы начинаете изучать мир...
Система управления парковками с использованием HTML, CSS и JavaScript
Система управления парковками с использованием HTML, CSS и JavaScript
Веб-сайт по управлению парковками был создан с использованием HTML, CSS и JavaScript. Это простой сайт, ничего вычурного. Основная цель -...
JavaScript Вопросы с множественным выбором и ответы
JavaScript Вопросы с множественным выбором и ответы
Если вы ищете платформу, которая предоставляет вам бесплатный тест JavaScript MCQ (Multiple Choice Questions With Answers) для оценки ваших знаний,...
6
0
9 306
10

Ответы 10

Вы уверены, что X-Path реализован в вашей версии Internet Explorer? Например: какую версию вы используете?

Взгляните на проект http://dev.abiss.gr/sarissa/. Они перенесли большинство API, связанных с XML, в IE. В противном случае это действительно также легко реализовать. Проблемы, которые вам необходимо решить, будут следующими: сериализация HTML в действительный XML, синхронизация результата запроса XMLDOM XPath с исходным HTMLDOM. Насколько мне известно, они сделали это в своей библиотеке, однако производительность могла бы быть лучше.

jQuery реализует кроссбраузерно совместимое подмножество селекторов xPath с подключаемым модулем. Ваш пример "/ HTML / BODY / DIV [9] / DIV [2]" должен работать в нем.

(править - исправлено спасибо Сергею Ильинскому)

jQuery НЕ реализует XPath. Он реализует очень простую функцию выбора пути (что составляет около 0,01% от XPath).

Sergey Ilinsky 07.10.2008 16:37

Вместо того, чтобы делать

xmlDoc.load(document); 

пытаться

xmlDoc.loadXML(document.body.outerHTML)

Это действительно будет работать, только если ваш HTML-документ отформатирован в соответствии со стандартами XHTML. Кроме того, тег BODY будет корневым узлом, поэтому вам придется изменить XPATH на "/ BODY / DIV [9] / DIV [2]"

Я бы немного побеспокоился об использовании подобного xml, так как вы не можете быть уверены, какая версия (если есть) XML DLL у человека. Все еще есть компании, использующие IE5.0 в массовом порядке, а в 5.5 была особенно гибкая реализация XML.

Привет, в конце концов, я придумал свое собственное хитрое решение, любые предложения по его улучшению были бы очень признательны. Он использует некоторые функции прототипа:

Работает в IE5 + с xpath в форме "/ HTML / BODY / DIV [9] / DIV [2]"

function getXPathElement (xpath, element) {

//Specific to project, here i know that the body element will always have the id "top"
//but otherwise the element that is passed in should be first element in the xpath 
//statement eg. /HTML/BODY/DIV the element passed in should be HTML
if (!element){
    element = $("top");
    var xpathArrayIndex = 3;
} else {
    var xpathArrayIndex = 1;
}
//split the xpath statement up
var xpathArray = xpath.split("/");

var carryOn = true; 
while(carryOn){
    decendents = element.childElements();
    //check to see if we are at the end of the xpath statement
    if (xpathArrayIndex == xpathArray.length){
        return element;
    }
    //if there is only one decendent make it the next element
    if (decendents.size() == 1) {
        element = decendents.first();
    } else {
    //otherwise search the decendents for the next element
        element = getXPathElementByIndex(decendents, xpathArray[xpathArrayIndex]);
    }
    xpathArrayIndex++;
}

}

function getXPathElementByIndex (потомки, xpathSegment) {

var decendentsArray = decendents.toArray();
//seperate the index from the element name
var temp = xpathSegment.split("[");
var elementName = temp[0];
//get the index as a number eg. "9]" to 9
var elementIndex = +temp[1].replace("]", "");
//the number of matching elements
var count = 0;

//keeps track of the number of iterations
var i = 0;
while(count != elementIndex) {
    //if the decendent's name matches the xpath element name increment the count
    if (decendentsArray[i].nodeName == elementName){
        count++;
    }
    i++;
}
var element = decendentsArray[i - 1];
return element;

}

Спасибо всем за помощь, в любом случае я немного узнал о различных фреймворках javascript.

Другую реализацию W3C Dom Level 3 XPath в JavaScript можно найти на Source Forge. Но не проявляет активности.

Проблема может заключаться в том, что в IE5 + [1] на самом деле [2] в FF. Microsoft единолично решила, что нумерация должна начинаться с [0], а не с [1], как указано w3c.

Я не могу найти простое и распространенное решение, вы можете написать собственную функцию для реализации небольшого количества xpath, но это сложно сделать в Internet Explorer 6 или более ранней версии ....

В коде oly1234 есть некоторые ошибки, которые я пытаюсь исправить следующим образом:

function getXPathElement(xpath, element){
if (!element){
    element = document;
}
var xpathArray = xpath.split("/");

element = findXPathRoot(xpathArray[0],xpathArray[1],element);

for(var i=1; i<xpathArray.length; i++){
    if (xpathArray[i].toLowerCase()= = "html"){
        continue;
    }
    if (!element){
        return element;
    }
    element = getXPathElementByIndex(element.childNodes,xpathArray[i]);         
}
return element;
}


function findXPathRoot(rootPath,htmlPath,element){
if (rootPath == ""&&htmlPath.toLowerCase() == "html"){
    return element.documentElement;
}
return document.getElementsByTagName(rootPath)[0];
}
function getXPathElementByIndex(decendents, xpathSegment){
//seperate the index from the element name
var temp = xpathSegment.split("[");
var elementName = temp[0];
//get the index as a number eg. "9]" to 9
if (temp[1]){
    var elementIndex = temp[1].replace("]", "");
}else{
    var elementIndex = 1;
}
//the number of matching elements
var count = 0;
for(var i=0;i < decendents.length; i++){
    if (decendents[i].nodeName.toLowerCase() == elementName.toLowerCase()) {
        count++;
        if (count==elementIndex){
            return decendents[i];
        }
    }
}
return null;
}

Другие вопросы по теме