JAXB--@XmlElementWrapper注解和泛型一起使用
当java对象的某个属性使用泛型时,普通对象都没问题,但是遇到HashSet这种集合类封装的元素时,就会出现元素内容序列化不出来的问题,详见如下:
一、示例:
第一步:定义java对象
- package step3;
- import javax.xml.bind.annotation.XmlAccessType;
- import javax.xml.bind.annotation.XmlAccessorType;
- import javax.xml.bind.annotation.XmlRootElement;
- @XmlRootElement
- @XmlAccessorType(value = XmlAccessType.PROPERTY)
- public class Customer<T> {
- String name;
- int age;
- int id;
- T t;
- public String getName() {
- return name;
- }
- public void setName(String name) {
- this.name = name;
- }
- public int getAge() {
- return age;
- }
- public void setAge(int age) {
- this.age = age;
- }
- public int getId() {
- return id;
- }
- public void setId(int id) {
- this.id = id;
- }
- @Override
- public String toString() {
- return "Customer [id=" + id + ",name=" + name + ",age=" + age + ",t=" + t + "]";
- }
- public T getT() {
- return t;
- }
- public void setT(T t) {
- this.t = t;
- }
- }
- package step3;
- import javax.xml.bind.annotation.XmlAccessType;
- import javax.xml.bind.annotation.XmlAccessorType;
- @XmlAccessorType(value = XmlAccessType.PROPERTY)
- public class Book {
- private String id;
- private String name;
- private float price;
- public String getId() {
- return id;
- }
- public void setId(String id) {
- this.id = id;
- }
- public String getName() {
- return name;
- }
- public void setName(String name) {
- this.name = name;
- }
- public float getPrice() {
- return price;
- }
- public void setPrice(float price) {
- this.price = price;
- }
- @Override
- public String toString() {
- return "Book [id=" + id + ",name=" + name + ",price=" + price + "]";
- }
- }
第二步:编组(JAXBContext.newInstance(Customer.class,HashSet.class);方法添加了
HashSet的class对象,以提供给JAXBContext使用。)
- package step3;
- import java.io.File;
- import java.util.HashSet;
- import javax.xml.bind.JAXBContext;
- import javax.xml.bind.JAXBException;
- import javax.xml.bind.Marshaller;
- //Marshaller
- public class Object2XmlDemo {
- public static void main(String[] args) {
- Customer<HashSet<Book>> customer = new Customer<HashSet<Book>>();
- customer.setId(100);
- customer.setName("suo");
- customer.setAge(29);
- Book book = new Book();
- book.setId("1");
- book.setName("哈里波特");
- book.setPrice(100);
- Book book2 = new Book();
- book2.setId("2");
- book2.setName("苹果");
- book2.setPrice(50);
- HashSet<Book> bookSet = new HashSet<Book>();
- bookSet.add(book);
- bookSet.add(book2);
- customer.setT(bookSet);
- try {
- File file = new File("C:\\file1.xml");
- JAXBContext jaxbContext = JAXBContext.newInstance(Customer.class,
- HashSet.class);
- Marshaller jaxbMarshaller = jaxbContext.createMarshaller();
- // output pretty printed
- jaxbMarshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
- jaxbMarshaller.marshal(customer, file);
- jaxbMarshaller.marshal(customer, System.out);
- } catch (JAXBException e) {
- e.printStackTrace();
- }
- }
- }
得到的xml:
- <?xml version="1.0" encoding="UTF-8" standalone="yes"?>
- <customer>
- <age>29</age>
- <id>100</id>
- <name>suo</name>
- <t xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:type="hashSet"/>
- </customer>
注:
1.泛型使用集合元素替代时,泛型属性所对应的xml没有序列化出来。
2.若JAXBContext.newInstance(Customer.class,HashSet.class);不添加HashSet
的class对象,则报错:
[javax.xml.bind.JAXBException: class java.util.HashSet nor any of its super class is known to this context.]
解决办法:
第一步:新增HashSet的包装类
Book类和Customer类相关代码均不需要改变,新增一个HashSet的包装类,定义如下:
- package step4;
- import java.util.HashSet;
- import javax.xml.bind.annotation.XmlElement;
- import javax.xml.bind.annotation.XmlElementWrapper;
- public class BookSet {
- private HashSet<Book> bookSet = new HashSet<Book>();
- //仅包含get方法,未包含set方法
- @XmlElementWrapper(name = "bookSet")//该注解非必须,仅是标注集合元素
- @XmlElement(name="book")
- public HashSet<Book> getBookSet() {
- return bookSet;
- }
- public void addBook(Book book){
- bookSet.add(book);
- }
- }
注:
1.BookSet类内部使用HashSet实现.
2.BookSet类在get方法上添加了@XmlElementWrapper(name = "bookSet")注解。
第二步:编组
- package step4;
- import java.io.File;
- import javax.xml.bind.JAXBContext;
- import javax.xml.bind.JAXBException;
- import javax.xml.bind.Marshaller;
- //Marshaller
- public class Object2XmlDemo {
- public static void main(String[] args) {
- Customer<BookSet> customer = new Customer<BookSet>();
- customer.setId(100);
- customer.setName("suo");
- customer.setAge(29);
- Book book = new Book();
- book.setId("1");
- book.setName("哈里波特");
- book.setPrice(100);
- Book book2 = new Book();
- book2.setId("2");
- book2.setName("苹果");
- book2.setPrice(50);
- BookSet bookSet = new BookSet();
- bookSet.addBook(book);
- bookSet.addBook(book2);
- customer.setT(bookSet);
- try {
- File file = new File("C:\\file1.xml");
- JAXBContext jaxbContext = JAXBContext.newInstance(Customer.class,
- BookSet.class);
- Marshaller jaxbMarshaller = jaxbContext.createMarshaller();
- // output pretty printed
- jaxbMarshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
- jaxbMarshaller.marshal(customer, file);
- jaxbMarshaller.marshal(customer, System.out);
- } catch (JAXBException e) {
- e.printStackTrace();
- }
- }
- }
注:
1.定义Customer对象时,使用包装类,即:
Customer<BookSet> customer = new Customer<BookSet>();
2.JAXBContext调用newInstance()方法时,传入BookSet的class对象,告知BookSet的类型,即:JAXBContext.newInstance(Customer.class,BookSet.class);
得到的xml:
- <?xml version="1.0" encoding="UTF-8" standalone="yes"?>
- <customer>
- <age>29</age>
- <id>100</id>
- <name>suo</name>
- <t xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:type="bookSet">
- <bookSet>
- <book>
- <id>2</id>
- <name>苹果</name>
- <price>50.0</price>
- </book>
- <book>
- <id>1</id>
- <name>哈里波特</name>
- <price>100.0</price>
- </book>
- </bookSet>
- </t>
- </customer>
JAXB--@XmlElementWrapper注解和泛型一起使用相关推荐
- JAXB 中的@XmlElementWrapper注解生成问题
JAXB 中的@XmlElementWrapper注解生成问题 1. 面临的问题场景 XHTML 1 2 3 4 5 6 7 <?xml version="1.0" enco ...
- JAXB常用注解讲解(超详细)
简介: JAXB(Java Architecture for XML Binding) 是一个业界的标准,是一项可以根据XML Schema产生Java类的技术.该过程中,JAXB也提供了将XML实例 ...
- 黑马程序员---基础加强-----------------第二天(新特性:注解、泛型)
注解:相当于一种标记,在程序中加了注解就等于为程序打上了某种标记,没加,则等于没有某种标记. 以后,javac编译器,开发工具和其他程序可以用反射来了解你的类及各种元素上有无何种标记,看你有什么标记, ...
- 使用@RequestParam注解和泛型遇到的问题
@RequestParam注解的作用是给传入的参数起一个别名,但是当参数中含有泛型的时候,该注解无法识别泛型 去掉@RequestParam注解之后
- JAVA面试-基础加强与巩固:反射、注解、泛型等
https://www.jianshu.com/p/aaf8594e02eb 企业重视的是学习能力:基础很重要 JDK1.5新特性 泛型 foreach 自动拆箱装箱 枚举 静态导入(Static i ...
- 黑马程序员 高新技术三 注解和泛型
----------android培训 java培训 期待与您交流! ---------- 第一节 了解和入门注解的应用 一.概述: 注解相当于一种标记,在程序中加了注解就等于为程序打上了某种标记,没 ...
- Java_比较器枚举类和注解集合泛型
文章目录 Java_比较器 Java_自然排序:java.lang.Comparable Java_Comparable的实现 Java_定制排序java.util.Comparator Java_S ...
- java泛型和注解,泛型 · 注解和泛型 · 看云
[TOC] # 泛型 ## 为什么要使用泛型 在之前学过的集合框架中,List和Map都使用了泛型技术来确认其内容的数据类型. 如果不使用泛型,在程序运行阶段,会带来数据类型转型的错误风险. ~~~ ...
- HowToDoInJava 其它教程 2 · 翻译完毕
原文:HowToDoInJava 协议:CC BY-NC-SA 4.0 欢迎任何人参与和完善:一个人可以走的很快,但是一群人却可以走的更远. ApacheCN 学习资源 目录 JMS 教程 JMS 教 ...
最新文章
- Token 防盗链详解
- T级的备份兄弟们都怎么做
- 牛客 - Gaming with Mia(dp)
- 简单的企业微信开发 前后端
- 针对新手的Java EE7和Maven项目–第1部分–简单的Maven项目结构–父pom
- pytorch深度学习-微调(fine tuning)
- pta段错误是什么意思_用Python执行Django数据迁移时报!(1091错误及解决方法)...
- ORM框架SQLAlchemy使用学习
- C# 打开文件 保存文件
- lcl手术和飞秒区别_关于全飞秒价格的那些事!你知道吗?
- (四)DIH导入结构化数据
- 小黑算法成长日记11:基于Johnson算法de最优流水作业调度
- 安装AdventureWorks2008R2
- 深度步态识别综述(三)
- 开启电脑卓越性能模式
- 梨花带雨html音乐播放器源码,梨花带雨 - 雨陌文化传媒 - 5SING中国原创音乐基地...
- 以5‰的概率计算一个网络准确率达到99.9%的时间和迭代次数---实例三分类mnist 3,4,5
- 【JavaSE进阶(上)】自学笔记 记得收藏时时回顾
- 室内导航将成为杀手级应用
- 淘宝近12亿条用户信息泄露,犯罪分子获利34万
热门文章
- 一套图 搞懂“时间复杂度”
- 深度学习经典案例解析:YOLO系列
- 详解Python拼接字符串的七种方式
- 深度对话林元庆:AI创业历史性窗口到来,将诞生下个BAT
- SAP QM 采购货物收到第三方仓库,转库回工厂仓库之后质检之处理
- 走向通用智能的核心:任务树的建立
- 专访王田苗:机器人是“刚需”,市场正处于逆周期增长
- 机器学习奠基人Michael Jordan:下代技术是融合经济学,解读2项重要进展
- 美国在人工智能领域亟待解决的5大难题
- 模拟人脑项目彻底宣告失败:耗资10亿欧,10年前轰动全球,如今死得悄无声息...