使用Java解析xml(获取可选的childnode值)

使用Java解析xml(获取可选的childnode值),java,xml,Java,Xml,我需要解析一个名为students的xml文件,每个学生都有rollno、firstname、lastname作为属性,但不是所有学生都有一个俱乐部。 xml文件如下所示: <?xml version="1.0"?> <class> <student rollno="393" firstname="Dinkar" lastname="Kad"> <club name="Asian-Caucus" /> </student&

我需要解析一个名为students的xml文件,每个学生都有rollno、firstname、lastname作为属性,但不是所有学生都有一个俱乐部。 xml文件如下所示:

<?xml version="1.0"?>
<class>
   <student rollno="393" firstname="Dinkar" lastname="Kad">
    <club name="Asian-Caucus" />
   </student>
   <student rollno="493" firstname="Vaneet" lastname="Gupta"/>
   <student rollno="593" firstname="jasvir" lastname="jazz">
      <club name="Students-for-Corporate-Citizenship"/>
   </student>
   <student rollno="693" firstname="Joseph" lastname="Patterson"/>
</class>

我想检索每个学生的信息,获取他们的学号、名字、姓氏和俱乐部名称(如果存在)。 我的代码可以获取有关所需属性的信息,但俱乐部名称始终为空(即使应该有与此学生关联的俱乐部): 我的代码如下所示:

    import java.io.File;
    import java.util.ArrayList;
    import java.util.List;

    import javax.xml.parsers.DocumentBuilder;
    import javax.xml.parsers.DocumentBuilderFactory;

    import org.w3c.dom.Document;
    import org.w3c.dom.Element;
    import org.w3c.dom.NamedNodeMap;
    import org.w3c.dom.Node;
    import org.w3c.dom.NodeList;


    public class TestParser {


        public void parseXML() throws Exception{
              DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
              DocumentBuilder docBuilder = factory.newDocumentBuilder();
              File file = new File("c:\\My Documents\\students.xml");
              Document doc = docBuilder.parse(file);




              NodeList list = doc.getElementsByTagName("student");
              for(int i=0; i<list.getLength(); i++){

                  int rollno = 0;
                  String firstname = "";
                  String lastname = "";
                  String clubname  = "";

                  Element cur = (Element)list.item(i);

                  NamedNodeMap curAttr = cur.getAttributes();


                  for(int j=0; j<curAttr.getLength(); j++){
                      Node attr = curAttr.item(j);
                      if(attr.getNodeName().equals("rollno"))
                          rollno = Integer.parseInt(attr.getNodeValue());
                      if(attr.getNodeName().equals("firstname")) 
                          firstname = attr.getNodeValue();
                      if(attr.getNodeName().equals("lastname")) 
                          lastname = attr.getNodeValue();
                      if(attr.getNodeName().equals("club name")) 
                          clubname = attr.getNodeValue();

                  } // end for each attribute
                  System.out.print("rollno: " + rollno);
                  System.out.print(" firstname: " + firstname);
                  System.out.print(" lastname: " + lastname);
                  System.out.println(" club name: " + clubname);



              }// end for each element


        }     


        public static void main(String[] args) throws Exception {
            // TODO Auto-generated method stub
            TestParser tp = new TestParser();
            tp.parseXML();

        }

    }



Output looks like this:

    rollno: 393 firstname: Dinkar lastname: Kad club name: 
    rollno: 493 firstname: Vaneet lastname: Gupta club name: 
    rollno: 593 firstname: jasvir lastname: jazz club name: 
    rollno: 693 firstname: Joseph lastname: Patterson club name: 

Any idea to fix this problem, so that student has a club can print out the correct club name? I'm very new to xml parsing, any suggestion is appreciated. Thanks a lot!
导入java.io.File;
导入java.util.ArrayList;
导入java.util.List;
导入javax.xml.parsers.DocumentBuilder;
导入javax.xml.parsers.DocumentBuilderFactory;
导入org.w3c.dom.Document;
导入org.w3c.dom.Element;
导入org.w3c.dom.NamedNodeMap;
导入org.w3c.dom.Node;
导入org.w3c.dom.NodeList;
公共类测试分析器{
public void parseXML()引发异常{
DocumentBuilderFactory工厂=DocumentBuilderFactory.newInstance();
DocumentBuilder docBuilder=factory.newDocumentBuilder();
File File=新文件(“c:\\My Documents\\students.xml”);
Document doc=docBuilder.parse(文件);
NodeList list=doc.getElementsByTagName(“学生”);

对于(int i=0;i,您需要获取俱乐部节点,然后通过其属性循环-类似于您已经使用的方式

       //check if there is any optional childnode
          if(cur.hasChildNodes()) {
            NodeList stChildNodes = cur.getChildNodes();
             // Loop through all the nodes and find the club node only
            for(Node child : stChildNodes) {
              if(child.getNodeName().equals("club") {
                  //"club" node detected. now loop through the attributes like the way you already did for students
                  NamedNodeMap clubAttr = child.getAttributes();
                  for(int j=0; j<clubAttr.getLength(); j++){
                    Node clattr = clubAttr.item(j);
                    if(clattr.getNodeName().equals("name")) {
                      clubname = clattr.getNodeValue();
                    }
                  }
                  break; // probably we are not interested in other nodes
               }
             }
          }
//检查是否有任何可选的子节点
if(cur.hasChildNodes()){
NodeList stChildNodes=cur.getChildNodes();
//循环遍历所有节点并仅查找俱乐部节点
用于(节点子节点:stChildNodes){
if(child.getNodeName().equals(“俱乐部”){
//检测到“俱乐部”节点。现在,像您为学生所做的那样循环属性
NamedNodeMap clubAttr=child.getAttributes();

对于(int j=0;j,属性名称不是“club name”。club是元素的名称,“name”是属性。您可以通过cur.getChildNodes()访问club节点……感谢提示anwser。我尝试将like更改为
if(attr.getNodeName().equals(“name”))clubname=attr.getNodeValue()
但这没有任何区别。@tanjir谢谢。我之前试过这个。结果不太对劲。请你提供一个代码片段好吗?谢谢!非常感谢!我修改了一点,现在效果很好!我已经编辑了原始帖子和你的答案。很高兴听到这一点。你已经非常接近了哎……)
       //check if there is any optional childnode
          if(cur.hasChildNodes()) {
            NodeList stChildNodes = cur.getChildNodes();
             // Loop through all the nodes and find the club node only
            for(Node child : stChildNodes) {
              if(child.getNodeName().equals("club") {
                  //"club" node detected. now loop through the attributes like the way you already did for students
                  NamedNodeMap clubAttr = child.getAttributes();
                  for(int j=0; j<clubAttr.getLength(); j++){
                    Node clattr = clubAttr.item(j);
                    if(clattr.getNodeName().equals("name")) {
                      clubname = clattr.getNodeValue();
                    }
                  }
                  break; // probably we are not interested in other nodes
               }
             }
          }