XML auslesen - Kinder von Kinder auslesen

Hallo,
ich möchte gerne folgende XML mit JDOM auslesen:

<?xml version="1.0" encoding="UTF-8"?>
<myapp version="1.0">
<photo_information>
  <date>2016/08/20</date>
  <time>17:21:59</time>
  <user_data></user_data>
  <prints>1</prints>
  <photos>
    <photo image="1">IMG_0001.JPG</photo>
    <photo image="2">IMG_0002.JPG</photo>
    <photo image="3">IMG_0003.JPG</photo>
    <photo image="4">IMG_0004.JPG</photo>
    <output>prints\160820_172159.jpg</output>
  </photos>
</photo_information>
</myapp>

Im Moment sieht das so bei mir aus:


            Document document = (Document) builder.build(xmlFile);
            Element rootNode = document.getRootElement();
            List list = rootNode.getChildren("photo_information");
           
            Element node = (Element) list.get(0);
            System.out.println("Date : " + node.getChildText("date"));
            System.out.println("Prints : " + node.getChildText("prints"));

            for (int i = 0; i < list.size(); i++) {

                List list2 = node.getChildren("photos");
                for (int l = 0; l < list2.size(); l++) {
                    Element node2 = (Element) list2.get(l);
                    System.out.println("Photo : " + node2.getChildText("photo"));
                }
            }

        } catch (IOException io) {
            System.out.println(io.getMessage());
        } catch (JDOMException jdomex) {
            System.out.println(jdomex.getMessage());
        }```

Mein Output:

Date : 2016/08/20
Prints : 1
Photo : IMG_0001.JPG



Wie bekomme ich aber noch die anderen Photos + Output?
Derzeit bekomme ich nur ein Photo.
Also sprich, wie bekomme ich noch die Werte von:


IMG_0002.JPG
IMG_0003.JPG
IMG_0004.JPG
prints\160820_172159.jpg



Danke für jede Hilfe

Irgend 'ne Idee, wenn Du auf diese Zeile schaust?

bye
TT

Ne, weiß nicht worauf Du hinauswillst.
Die liest mir den Knoten <photo_information> aus, da ich nur einen davon habe, kann ich das erste Objekt nehmen…

den Gedankensprung sehe ich auch nicht allzu sehr,
aber weiter überlegt, wieviele Knoten gibt es? die gelieferte Anzahl 1 wohl doch nicht so falsch,
kommt man von einem photos-Element noch weiter?..

die i-Schleife ist im Moment übrigens nicht gut im Programm, da du mit i nichts machst,
zum Glück nur genau ein Element in der ersten list, sonst wäre allles mehrfach ausgeführt

Nur so als Hinweis: In deinem Fall ist JAXB wahrscheinlich bequemer als JDOM, du erstellst einfach eine Klasse, die die gleiche Struktur wie dein XML hat, annotierst ein bisschen, und dann übernimmt JAXB das Einlesen.

Beispiel: https://www.mkyong.com/java/jaxb-hello-world-example/

[QUOTE=Landei]Nur so als Hinweis: In deinem Fall ist JAXB wahrscheinlich bequemer als JDOM, du erstellst einfach eine Klasse, die die gleiche Struktur wie dein XML hat, annotierst ein bisschen, und dann übernimmt JAXB das Einlesen.

Beispiel: https://www.mkyong.com/java/jaxb-hello-world-example/[/QUOTE]

ok, aber wie muss ich dann die in der Klasse annotieren, da es ja mehrere Photos gibt? Brauche ich für die Photos nochmals eine weitere Klasse?

IMG_0001.JPG IMG_0002.JPG IMG_0003.JPG IMG_0004.JPG prints\160820_172159.jpg

Liste vielleicht wie hier
xml - JAXB: How to marshal objects in lists? - Stack Overflow

wobei das output-Attribut für photos noch Herausforderung wäre…

hm, wo wirklich helfen tut mir das nicht.
Hat keiner einer Idee, wie man das lösen kann?

bist du noch bei JDOM? meinen Beitrag 10:46 gesehen?
der war ja nicht mehr ganz so rätselhaft
-> node2.getChildren()

[QUOTE=SlaterB]
-> node2.getChildren()[/QUOTE]

das hatte ich gestern auch probiert, leider hat das auch nicht funktioniert…

was passiert denn stattdessen?

ich habe dein Programm nachgebaut, wenn auch mit Mühe bei Unvollständigkeit, und erhalte bei

    public static void main(String[] args)    throws Exception  {
        DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
        DocumentBuilder dombuilder = factory.newDocumentBuilder();
        org.w3c.dom.Document w3cDocument = dombuilder.parse("text.xml");
        DOMBuilder docBuilder = new DOMBuilder();

        Document document = docBuilder.build(w3cDocument);
        Element rootNode = document.getRootElement();

        Element node = rootNode.getChild("photo_information");
        System.out.println("Date : " + node.getChildText("date"));
        System.out.println("Prints : " + node.getChildText("prints"));

        List list2 = node.getChildren("photos");
        for (int l = 0; l < list2.size(); l++)
        {
            Element node2 = (Element)list2.get(l);
            System.out.println("Photo : " + node2.getChildText("photo"));
            System.out.println(node2.getChildren());
        }
    }
}

->

Date : 2016/08/20
Prints : 1
Photo : IMG_0001.JPG
[[Element: <photo/>], [Element: <photo/>], [Element: <photo/>], [Element: <photo/>], [Element: <output/>]]

was liefert denn getChildren() bei dir an dieser Stelle, eine leere Liste?
liefert getContent() etwas?

@TO Du solltest ein wenig an deiner Einstellung arbeiten. Wir helfen hier gerne, aber ein bisschen Eigeninitiative sollte schon kommen.

Aber ich will mal nicht so sein, hier die einfachste JAXB-Version:

import javax.xml.bind.JAXBContext;
import javax.xml.bind.JAXBException;
import javax.xml.bind.Unmarshaller;
import java.io.File;

public class Test {

    public static void main(String[] args) {
        try {
            File file = new File("myapp.xml");
            JAXBContext jaxbContext = JAXBContext.newInstance(MyApp.class);
            Unmarshaller jaxbUnmarshaller = jaxbContext.createUnmarshaller();
            MyApp myApp = (MyApp) jaxbUnmarshaller.unmarshal(file);
            System.out.println(myApp);
        } catch (JAXBException e) {
            e.printStackTrace();
        }

    }
}```

```import javax.xml.bind.annotation.XmlElement;
import javax.xml.bind.annotation.XmlRootElement;
import java.util.List;

@XmlRootElement(name = "myapp")
public class MyApp {

    private List<PhotoInfo> photoInfoList;

    public List<PhotoInfo> getPhotoInfoList() {
        return photoInfoList;
    }

    @XmlElement(name = "photo_information")
    public void setPhotoInfoList(List<PhotoInfo> photoInfoList) {
        this.photoInfoList = photoInfoList;
    }
}

public class PhotoInfo {

    private String date;
    private String time;
    private String userData;
    private int prints;
    private Photos photos;

    public String getDate() {
        return date;
    }

    @XmlElement
    public void setDate(String date) {
        this.date = date;
    }

    public String getTime() {
        return time;
    }

    @XmlElement
    public void setTime(String time) {
        this.time = time;
    }

    public String getUserData() {
        return userData;
    }

    @XmlElement
    public void setUserData(String userData) {
        this.userData = userData;
    }

    public int getPrints() {
        return prints;
    }

    @XmlElement
    public void setPrints(int prints) {
        this.prints = prints;
    }

    public Photos getPhotos() {
        return photos;
    }

    @XmlElement
    public void setPhotos(Photos photos) {
        this.photos = photos;
    }
}
import java.util.List;

public class Photos {
    List<Photo> photo;
    String output;

    public List<Photo> getPhoto() {
        return photo;
    }

    @XmlElement
    public void setPhoto(List<Photo> photo) {
        this.photo = photo;
    }

    public String getOutput() {
        return output;
    }

    @XmlElement
    public void setOutput(String output) {
        this.output = output;
    }
}
import javax.xml.bind.annotation.XmlValue;

public class Photo {
    private int image;

    public int getImage() {
        return image;
    }

    @XmlAttribute
    public void setImage(int image) {
        this.image = image;
    }

    public String getName() {
        return name;
    }

    @XmlValue
    public void setName(String name) {
        this.name = name;
    }

    private String name;
}

Wenn output nicht in der photos-collection wäre (oder z.B. ein Attribut von photos), brauchte man die Photos-Klasse nicht, sondern könnte die Photo-Liste gleich in PhotoInfo auslesen (mit einer zusätzlichen @XmlElementWrapper(name="photos")-Annotation). Datum und Zeit sind hier erst mal String - das bekommt auch netter hin, aber ein bisschen anstrengen solltest du dich ruhig auch…