在每个方法调用中使用newInstance()创建JAXBContext有多少权利?

时间:2018-10-24 08:16:43

标签: java jaxb

在春季启动项目中,我创建了JAXBContext bean:

@Configuration
public class MarshallerConfig {

    @Bean
    JAXBContext jaxbContext() throws JAXBException {
        return JAXBContext.newInstance(my packages);
    }
}

然后我创建包装器以使用此上下文:

@Component
public class MarshallerImpl implements Marshaler {

    private final JAXBContext jaxbContext;

    public MarshallerImpl(JAXBContext jaxbContext) {
        this.jaxbContext = jaxbContext;
    }

     //murshall and unmarshal methosds imlementation
    }

当我像bean创建JAXBContext时-我知道这个JAXBContext将是单例的。但是,现在我需要在没有@XMLRootElement注释的情况下为marshall元素实现marhall方法。我在article

中实现它
@Override
public <T> String marshalToStringWithoutRoot(T value, Class<T> clazz) {
    try {
        StringWriter stringWriter = new StringWriter();

        JAXBContext jc = JAXBContext.newInstance(clazz);
        Marshaller marshaller = jc.createMarshaller();
        // format the XML output
        marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, false);

        QName qName = new QName(value.getClass().getPackage().toString(), value.getClass().getSimpleName());
        JAXBElement<T> root = new JAXBElement<>(qName, clazz, value);

        marshaller.marshal(root, stringWriter);

        return stringWriter.toString();
    } catch (JAXBException e) {
        throw new RuntimeException(e.getMessage());
    }
}

我将JAXBContext创建到方法JAXBContext jc = JAXBContext.newInstance(clazz);中。

它的正确性如何?每次使用newInstance创建对象吗?

我在此方法中稍稍看了一下,却没有发现这是一个单例。

1 个答案:

答案 0 :(得分:0)

由于创建JAXBContext非常耗时, 您应该尽可能避免使用它。

您可以通过将它们缓存在Map<Class<?>, JAXBContext>中来实现。

private static Map<Class<?>, JAXBContext> contextsByRootClass = new HashMap<>();

private static JAXBContext getJAXBContextForRoot(Class<?> clazz) throws JAXBException {
    JAXBContext context = contextsByRootClass.get(clazz);
    if (context == null) {
        context = JAXBContext.newInstance(clazz);
        contextsByRootClass.put(clazz, context);
    }
    return context;
}

最后,您可以使用marshalToStringWithoutRoot方法替换

JAXBContext jc = JAXBContext.newInstance(clazz);

作者

JAXBContext jc = getJAXBContextForRoot(clazz);