2016-07-19 5 views
1

Я пытаюсь маршализация один XML в ArrayList или к классу, но объект, который я сделать не заселен JAXBJAXB не демаршаллизации XML

@Override 
public Ships load(String xmlFilePath) { 
//Ships ship = new Ships(); 
ArrayList<Ship> shps = new ArrayList<>(); 
    try { 
    File file = new File(xmlFilePath); 
    JAXBContext jaxbContext = JAXBContext.newInstance(Ship.class); 

    Unmarshaller jaxbUnmarshaller = jaxbContext.createUnmarshaller(); 
    shps = (ArrayList<Ship>) jaxbUnmarshaller.unmarshal(file); 


    } catch (JAXBException e) { 
    e.printStackTrace(); 
    } 

return shps;} 
} 
+0

Какой ваш класс корабля и исходный вход xml? Кроме того, вы не должны бросать его в ArrayList. В конце концов вы можете получить CCE. – glee8e

+0

xml находится с этого корабля, но может быть проблемой, что корабль является интерфейсом? И я получаю только NullPointerExeption в конце программы, когда я пытаюсь что-то сделать с ArrayList. –

ответ

0

Может быть, вы уже читали это решение где-то еще, но наиболее распространенное решение состоит в том, чтобы сделать класс-оболочку (или даже лучше, общий, многоразовый класс-оболочку). В приведенном ниже коде есть рабочий пример этой концепции, я надеюсь, что код сам объясняет.

package com.quick; 

import java.io.ByteArrayInputStream; 
import java.io.ByteArrayOutputStream; 
import java.util.ArrayList; 
import java.util.List; 

import javax.xml.bind.JAXBContext; 
import javax.xml.bind.JAXBException; 
import javax.xml.bind.Marshaller; 
import javax.xml.bind.Unmarshaller; 
import javax.xml.bind.annotation.XmlAccessType; 
import javax.xml.bind.annotation.XmlAccessorType; 
import javax.xml.bind.annotation.XmlAnyElement; 
import javax.xml.bind.annotation.XmlRootElement; 

@XmlRootElement 
@XmlAccessorType(XmlAccessType.FIELD) // just to avoid the get and set methods 
class Wrapper<T> { 
    @XmlAnyElement 
    List<T> list; 
} 

@XmlRootElement 
@XmlAccessorType(XmlAccessType.FIELD) // just to avoid the get and set methods 
class Ship { 
    String id = "N" + System.nanoTime(); 
} 

public class Main { 

    public static void main(String[] args) throws JAXBException { 

     // context, marshaller and unmarshaller 
     JAXBContext context = JAXBContext.newInstance(Ship.class, Wrapper.class); 
     Marshaller marshaller = context.createMarshaller(); 
     marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); 
     Unmarshaller unmarshaller = context.createUnmarshaller(); 

     // original list 
     List<Ship> originalList = new ArrayList<>(); 
     originalList.add(new Ship()); 
     originalList.add(new Ship()); 
     originalList.add(new Ship()); 

     // wrapper object 
     Wrapper<Ship> originalWraper = new Wrapper<>(); 
     originalWraper.list = originalList; 

     // marshal the original wrapper and save the bytes in byteArray1 
     ByteArrayOutputStream os1 = new ByteArrayOutputStream(); 
     marshaller.marshal(originalWraper, os1); 
     byte[] byteArray1 = os1.toByteArray(); 

     // unmarshall the bytes 
     ByteArrayInputStream is = new ByteArrayInputStream(byteArray1); 
     Wrapper<Ship> unmarshaledWrapper = (Wrapper<Ship>) unmarshaller.unmarshal(is); 

     // THIS LIST SHOULD CONTAIN A COPY OF originalList 
     List<Ship> unmarshaledList = unmarshaledWrapper.list; 

     // marshal the unmarshaledWrapper (...) and sabe the bytes in byteArray2 
     ByteArrayOutputStream os2 = new ByteArrayOutputStream(); 
     marshaller.marshal(unmarshaledWrapper, os2); 
     byte[] byteArray2 = os2.toByteArray(); 

     // print the bytes, they should be the same 
     System.out.println(new String(byteArray1)); 
     System.out.println(new String(byteArray2)); 
    } 
} 

Общая идея состоит в том, чтобы сделать класс, который работает в качестве оболочки для вашего списка (или массива), которые могут быть маршалингом или маршалинга в соответствии с вашими потребностями.

Смежные вопросы