Ответ 1
Вы можете использовать XPath:
XPathFactory xpathFactory = XPathFactory.newInstance();
XPath xpath = xpathFactory.newXPath();
NodeList links = (NodeList) xpath.evaluate("rootNode/link", element,
XPathConstants.NODESET);
У меня есть XML файл следующим образом:
<rootNode>
<link>http://rootlink/</link>
<image>
<link>http://imagelink/</link>
<title>This is the title</title>
</image>
</rootNode>
XML-код Java с использованием DOM выглядит следующим образом:
NodeList rootNodeList = element.getElementsByTagName("link");
Это даст мне все элементы "ссылки", включая верхний уровень и тот, что находится внутри "изображения" node.
Есть ли способ получить теги "link" для rootNode на одном уровне, а не два, например, для ссылки на изображение? То есть я просто хочу http://rootlink/".
Вы можете использовать XPath:
XPathFactory xpathFactory = XPathFactory.newInstance();
XPath xpath = xpathFactory.newXPath();
NodeList links = (NodeList) xpath.evaluate("rootNode/link", element,
XPathConstants.NODESET);
Я не мог найти никаких методов для этого, так что я написал эту вспомогательную функцию,
public static List<Element> getChildrenByTagName(Element parent, String name) {
List<Element> nodeList = new ArrayList<Element>();
for (Node child = parent.getFirstChild(); child != null; child = child.getNextSibling()) {
if (child.getNodeType() == Node.ELEMENT_NODE &&
name.equals(child.getNodeName())) {
nodeList.add((Element) child);
}
}
return nodeList;
}
Если вы можете использовать JDOM, вы можете сделать это:
element.getChildren("link");
Со стандартным Dom, наиболее близким к которому вы можете воспользоваться, является итерация списка дочерних узлов (путем вызова getChildNodes() и проверки каждого элемента (i) NodeList, выделения узлов с соответствующим именем.
Я знаю, что это старый вопрос, но тем не менее у меня есть альтернативное решение для добавления.
Это не самый эффективный, но работает:
Получите всех детей, используя getElementsByTagName, а затем просто проверьте, что у каждого из них есть тот же родитель, что и тот, с которого вы начали.
Я использую это, потому что у меня есть набор результатов, каждый результат может иметь вложенные в него результаты. Когда я вызываю конструктор Result, мне нужно добавить любые вложенные результаты, но поскольку они сами будут искать своих собственных детей, я не хочу добавлять дочерние элементы на текущий уровень (их родитель будет добавлять их).
Пример:
NodeList children = resultNode.getElementsByTagName("result");
for(int i = 0; i<children.getLength(); i++){
// make sure not to pick up grandchildren.
if(children.item(i).getParentNode().isSameNode(resultNode)){
addChildResult(new Result((Element)children.item(i)));
}
}
Надеюсь, что это поможет.
Я написал эту функцию, чтобы получить значение node по имени tagName, ограничить верхний уровень
public static String getValue(Element item, String tagToGet, String parentTagName) {
NodeList n = item.getElementsByTagName(tagToGet);
Node nodeToGet = null;
for (int i = 0; i<n.getLength(); i++) {
if (n.item(i).getParentNode().getNodeName().equalsIgnoreCase(parentTagName)) {
nodeToGet = n.item(i);
}
}
return getElementValue(nodeToGet);
}
public final static String getElementValue(Node elem) {
Node child;
if (elem != null) {
if (elem.hasChildNodes()) {
for (child = elem.getFirstChild(); child != null; child = child
.getNextSibling()) {
if (child.getNodeType() == Node.TEXT_NODE) {
return child.getNodeValue();
}
}
}
}
return "";
}