- 浏览: 1061092 次
- 性别:
- 来自: 南京
文章分类
- 全部博客 (501)
- dwr (6)
- javascript (84)
- oracle (66)
- jsp/servlet (18)
- ant (3)
- 基础知识 (12)
- EXT (10)
- My SQL (10)
- java (71)
- spring (37)
- 学习的对象 (2)
- Linux (24)
- 面试 (1)
- HTML/CSS (11)
- tomcat (11)
- 收藏夹 (2)
- Power Designer (2)
- struts.xml配置文件 (1)
- sturts2 (3)
- myeclipse (8)
- eclipse (7)
- Maven (34)
- SVN (3)
- SAP JCO (2)
- JBOSS (11)
- webservice (8)
- word (1)
- 敏捷开发 (1)
- sybase (4)
- Nexus (3)
- EhCache (3)
- log4j (3)
- Cookie (4)
- Session (4)
- CXF (7)
- AXIS (2)
- SSO (1)
- LDAP (1)
- velocity (2)
- Jquery (5)
- redis (2)
- http (4)
- dojo (1)
- Linux资源监控软件mnon的安装与运用 (1)
- notepad++ (1)
- EA (1)
- UML (1)
- JasperReports (1)
- 权限 (0)
- freemarker (4)
- Spring MVC (1)
- JMS (1)
- activeMQ (1)
- hession (3)
- 安全 (1)
- ibatis (2)
- log (1)
- nginx (1)
最新评论
-
winhbb:
我刚好遇到了一个问题(在可以依赖注入的场合有效):有两个模块A ...
解决Maven项目相互依赖/循环依赖/双向依赖的问题 -
nanjiwubing123:
long3ok 写道你好 XmlOutputFormatter ...
用XStream转换复杂XML -
zhoujianboy:
另外一个方法实现eclipse tomcat 热部署:http ...
eclipse下实现maven项目在tomcat容器热部署方法 -
long3ok:
你好 XmlOutputFormatter 请问这个类是在什么 ...
用XStream转换复杂XML -
ganbo:
总结的好,文章给力。
解决Maven项目相互依赖/循环依赖/双向依赖的问题
[size=medium]最近在使用Google的Gson包进行Json和Java对象之间的转化,对于包含泛型的类的序列化和反序列化Gson也提供了很好的支持,感觉有点意思,就花时间研究了一下。
由于Java泛型的实现机制,使用了泛型的代码在运行期间相关的泛型参数的类型会被擦除,我们无法在运行期间获知泛型参数的具体类型(所有的泛型类型在运行时都是Object类型)。
但是有的时候,我们确实需要获知泛型参数的类型,比如将使用了泛型的Java代码序列化或者反序列化的时候,这个时候问题就变得比较棘手。
对于上面的类Foo<T>,由于在运行期间无法得知T的具体类型,对这个类的对象进行序列化和反序列化都不能正常进行。Gson通过借助TypeToken类来解决这个问题。
TypeToken的使用非常简单,如上面的代码,只要将需要获取类型的泛型类作为TypeToken的泛型参数构造一个匿名的子类,就可以通过getType()方法获取到我们使用的泛型类的泛型参数类型。
下面来简单分析一下原理。
要获取泛型参数的类型,一般的做法是在使用了泛型的类的构造函数中显示地传入泛型类的Class类型作为这个泛型类的私有属性,它保存了泛型类的类型信息。
这种方法虽然能解决问题,但是每次都要传入一个Class类参数,显得比较麻烦。Gson库里面对于这个问题采用了了另一种解决办法。
同样是为了获取Class的类型,可以通过另一种方式实现:
声明一个抽象的父类Foo,匿名子类将泛型类作为Foo的泛型参数传入构造一个实例,再调用getClass方法获得这个子类的Class类型。
这里虽然通过另一种方式获得了匿名子类的Class类型,但是并没有直接将泛型参数T的Class类型传进来,那又是如何获得泛型参数的类型的呢, 这要依赖Java的Class字节码中存储的泛型参数信息。Java的泛型机制虽然在运行期间泛型类和非泛型类都相同,但是在编译java源代码成 class文件中还是保存了泛型相关的信息,这些信息被保存在class字节码常量池中,使用了泛型的代码处会生成一个signature签名字段,通过 签名signature字段指明这个常量池的地址。
关于class文件中存储泛型参数类型的具体的详细的知识可以参考这里:http://stackoverflow.com/questions/937933/where-are-generic-types-stored-in-java-class-files
JDK里面提供了方法去读取这些泛型信息的方法,再借助反射,就可以获得泛型参数的具体类型。同样是对于第一段代码中的foo对象,通过下面的代码可以得到foo<T>中的T的类型:
运行结果是class java.lang.String。
分析一下这段代码,Class类的getGenericSuperClass()方法的注释是:
Returns the Type representing the direct superclass of the entity (class, interface, primitive type or void) represented by thisClass.
If the superclass is a parameterized type, the Type object returned must accurately reflect the actual type parameters used in the source code. The parameterized type representing the superclass is created if it had not been created before. See the declaration of ParameterizedType for the semantics of the creation process for parameterized types. If thisClass represents either theObject class, an interface, a primitive type, or void, then null is returned. If this object represents an array class then theClass object representing theObject class is returned
概括来说就是对于带有泛型的class,返回一个ParameterizedType对象,对于Object、接口和原始类型返回null,对于数 组class则是返回Object.class。ParameterizedType是表示带有泛型参数的类型的Java类型,JDK1.5引入了泛型之 后,Java中所有的Class都实现了Type接口,ParameterizedType则是继承了Type接口,所有包含泛型的Class类都会实现 这个接口。
实际运用中还要考虑比较多的情况,比如获得泛型参数的个数避免数组越界等,具体可以参看Gson中的TypeToken类及ParameterizedTypeImpl类的代码。[/size]
【转载地址】
http://www.blogjava.net/brock/archive/2012/08/01/384520.html
由于Java泛型的实现机制,使用了泛型的代码在运行期间相关的泛型参数的类型会被擦除,我们无法在运行期间获知泛型参数的具体类型(所有的泛型类型在运行时都是Object类型)。
但是有的时候,我们确实需要获知泛型参数的类型,比如将使用了泛型的Java代码序列化或者反序列化的时候,这个时候问题就变得比较棘手。
class Foo<T> { T value; } Gson gson = new Gson(); Foo<Bar> foo = new Foo<Bar>(); gson.toJson(foo); // May not serialize foo.value correctly gson.fromJson(json, foo.getClass()); // Fails to deserialize foo.value as Bar
对于上面的类Foo<T>,由于在运行期间无法得知T的具体类型,对这个类的对象进行序列化和反序列化都不能正常进行。Gson通过借助TypeToken类来解决这个问题。
TestGeneric<String> t = new TestGeneric<String>(); t.setValue("Alo"); Type type = new TypeToken<TestGeneric<String>>(){}.getType(); String gStr = GsonUtils.gson.toJson(t,type); System.out.println(gStr); TestGeneric t1 = GsonUtils.gson.fromJson(gStr, type); System.out.println(t1.getValue());
TypeToken的使用非常简单,如上面的代码,只要将需要获取类型的泛型类作为TypeToken的泛型参数构造一个匿名的子类,就可以通过getType()方法获取到我们使用的泛型类的泛型参数类型。
下面来简单分析一下原理。
要获取泛型参数的类型,一般的做法是在使用了泛型的类的构造函数中显示地传入泛型类的Class类型作为这个泛型类的私有属性,它保存了泛型类的类型信息。
public class Foo<T>{ public Class<T> kind; public Foo(Class<T> clazz){ this.kind = clazz; } public T[] getInstance(){ return (T[])Array.newInstance(kind, 5); } public static void main(String[] args){ Foo<String> foo = new Foo(String.class); String[] strArray = foo.getInstance(); } }
这种方法虽然能解决问题,但是每次都要传入一个Class类参数,显得比较麻烦。Gson库里面对于这个问题采用了了另一种解决办法。
同样是为了获取Class的类型,可以通过另一种方式实现:
public abstract class Foo<T>{ Class<T> type; public Foo(){ this.type = (Class<T>) getClass(); } public static void main(String[] args) { Foo<String> foo = new Foo<String>(){}; Class mySuperClass = foo.getClass(); } }
声明一个抽象的父类Foo,匿名子类将泛型类作为Foo的泛型参数传入构造一个实例,再调用getClass方法获得这个子类的Class类型。
这里虽然通过另一种方式获得了匿名子类的Class类型,但是并没有直接将泛型参数T的Class类型传进来,那又是如何获得泛型参数的类型的呢, 这要依赖Java的Class字节码中存储的泛型参数信息。Java的泛型机制虽然在运行期间泛型类和非泛型类都相同,但是在编译java源代码成 class文件中还是保存了泛型相关的信息,这些信息被保存在class字节码常量池中,使用了泛型的代码处会生成一个signature签名字段,通过 签名signature字段指明这个常量池的地址。
关于class文件中存储泛型参数类型的具体的详细的知识可以参考这里:http://stackoverflow.com/questions/937933/where-are-generic-types-stored-in-java-class-files
JDK里面提供了方法去读取这些泛型信息的方法,再借助反射,就可以获得泛型参数的具体类型。同样是对于第一段代码中的foo对象,通过下面的代码可以得到foo<T>中的T的类型:
Type mySuperClass = foo.getClass().getGenericSuperclass(); Type type = ((ParameterizedType)mySuperClass).getActualTypeArguments()[0]; System.out.println(type);
运行结果是class java.lang.String。
分析一下这段代码,Class类的getGenericSuperClass()方法的注释是:
Returns the Type representing the direct superclass of the entity (class, interface, primitive type or void) represented by thisClass.
If the superclass is a parameterized type, the Type object returned must accurately reflect the actual type parameters used in the source code. The parameterized type representing the superclass is created if it had not been created before. See the declaration of ParameterizedType for the semantics of the creation process for parameterized types. If thisClass represents either theObject class, an interface, a primitive type, or void, then null is returned. If this object represents an array class then theClass object representing theObject class is returned
概括来说就是对于带有泛型的class,返回一个ParameterizedType对象,对于Object、接口和原始类型返回null,对于数 组class则是返回Object.class。ParameterizedType是表示带有泛型参数的类型的Java类型,JDK1.5引入了泛型之 后,Java中所有的Class都实现了Type接口,ParameterizedType则是继承了Type接口,所有包含泛型的Class类都会实现 这个接口。
实际运用中还要考虑比较多的情况,比如获得泛型参数的个数避免数组越界等,具体可以参看Gson中的TypeToken类及ParameterizedTypeImpl类的代码。[/size]
【转载地址】
http://www.blogjava.net/brock/archive/2012/08/01/384520.html
发表评论
-
个人草稿使用
2017-08-19 09:02 0深入理解JVM: http://www.cnblogs.co ... -
Thread.setDaemon详解
2015-04-24 21:31 899java中线程分为两种类型:用户线程和守护线程。通过Threa ... -
怎么使用 ConcurrentHashMap 才能是线程安全的?
2015-04-13 11:54 1502public class test { public ... -
21,tomcat关闭钩子
2014-12-31 10:36 724在很多环境下,在关闭应用程序的时候需要做一些清理工作。问题在于 ... -
Java NIO使用及原理分析 (一) 【转载】
2014-10-24 00:04 484【转载】: http://blog.csdn.net/wuxi ... -
Java 两个集合取交集
2014-10-14 21:16 3122public static Set intersectionS ... -
Calendar类roll和add的区别
2014-10-10 22:28 489import java.text.SimpleDateForm ... -
HashMap的遍历效率讨论
2014-09-27 20:41 826经常遇到对HashMap中的key和value值对的遍历操作, ... -
Java 泛型
2014-06-26 12:44 852关键字说明 ? 通配符类型 <? extends T&g ... -
Java泛型集合的理解
2014-06-26 00:05 502[size=medium]什么是泛型? 泛型(Generic ... -
关于java字节码框架ASM的学习
2014-06-19 19:22 883一、什么是ASM ASM是一个java字节码操纵框架, ... -
Java动态代理详解
2014-06-19 17:41 857Java动态代理详解: http: ... -
Java内存,字符串文章收集
2014-06-18 16:24 714java--String常量池问题的几个例子 . http:/ ... -
Java内存解析
2014-06-18 11:48 773栈、堆、常量池等虽同 ... -
Java的堆与非堆内存
2014-01-07 10:59 713堆(Heap)和非堆(Non-heap)内存 按照官方的说法: ... -
JMX 资料收集
2014-01-07 10:53 449JavaSky的专栏 http://blog.csdn.net ... -
JAVA 注解示例 详解
2013-11-12 09:36 820注解(Annotation) 为我们在代码中天界信息提供了 ... -
Java 泛型详解
2013-11-11 22:35 796http://www.360doc.com/content/1 ... -
Java中的Enum的使用与分析
2013-11-09 12:49 814enum枚举类型:在实际问 ... -
Js中escape(),encodeURI()和encodeURIComponent()使用和比较:
2013-09-12 09:42 1029Js中escape(),encodeURI()和encodeU ...
相关推荐
当我们需要从JSON字符串反序列化到泛型类型时,可以创建一个泛型类型的`Gson`对象或使用`fromJson()`方法。例如,如果你有一个泛型列表`List<T>`,你可以这样做: ```java Type listType = new TypeToken...
json字符串实体bean或者List互转(gson和jackson,支持泛型),支持json的格式化,所需要的包在代码也有说明。还有少的可以告知我,谢谢
Gson解析json,实现泛型解析数据,根据用户传入的类型,解析称用户需要的,Common \CommonList 里面的status message data相关的约定可以更具开发者与服务器的约定修改
Json解析工具类完善一下,使用GSON+JsonPath+泛型来提高自己写JSON解析的效率 http://blog.csdn.net/b275518834/article/details/49819831
`TypeToken` 是 Gson 提供的一个泛型安全的类型引用,用于在运行时捕获和表示类型信息。 除了默认行为外,Gson 还支持通过注解(Annotations)进行更精细的控制。例如,你可以使用 `@Expose` 注解来指定哪些字段...
5. **类型安全的转换**:Gson的`fromJson()`方法支持传入`Type`或`TypeToken`参数,以确保反序列化的对象类型正确。 6. **流式API**:对于大型JSON数据,Gson提供了流式解析API,可以有效地处理大文件或网络流。 7...
处理泛型类型时,可以使用`TypeToken`来帮助Gson识别真实类型: ```java List<User> userList = gson.fromJson(jsonArrayString, new TypeToken<List<User>>(){}.getType()); ``` 五、注意事项 1. 数据类型匹配:...
当你需要将JSON解析到泛型类型时,可以使用`TypeToken`。例如,解析一个`List<Person>`: ```java Type listType = new TypeToken<List<Person>>(){}.getType(); List<Person> people = gson.fromJson...
- 当处理泛型类型时,如List或Map,需要提供具体的TypeToken来准确地反序列化。 - 示例中的`toJsonWithGson(Object obj, Type type)`方法即展示了如何处理带有泛型参数的类型。 #### 四、Gson工具类详解 根据...
1. **TypeToken**: 这个类用于存储泛型类型信息,因为Java的泛型在编译后会被擦除,TypeToken通过Class对象和参数化类型信息组合在一起,保存了泛型的实际类型信息。 2. **JsonSerializer<T> 和 JsonDeserializer**...
10. **类型安全的泛型**: Gson可以安全地处理泛型类型,避免运行时类型转换异常。 通过以上知识点,开发者可以充分利用Gson进行JSON数据的处理,无论是将Java对象转换为JSON以便在网络间传输,还是从接收到的JSON...
1. **类型安全的序列化与反序列化**:Gson允许开发者通过`Gson.toJson()`和`Gson.fromJson()`方法轻松地将Java对象转换为JSON字符串,反之亦然。这个过程是类型安全的,因为Gson会根据对象的类信息自动处理数据类型...
通过这些方法,JsonUtils工具类简化了Gson的使用,提高了代码的可读性和可维护性。开发者可以快速地在Java对象和JSON数据之间切换,无需关注底层实现细节。在项目中集成JsonUtils,可以极大地提升开发效率,同时保证...
Gson的核心类是`Gson`,它提供了`toJson()`和`fromJson()`两个方法,分别用于对象到JSON和JSON到对象的转换。然而,在处理枚举类型时,默认的Gson行为可能会有所局限,因为它通常只能处理枚举的名称(即枚举常量的...
- **类型转换的控制**:Gson允许开发者指定特定的类型转换规则,例如使用`TypeToken`来处理泛型类型。 - **字段映射的自定义**:通过注解如`@Expose`和`@SerializedName`,可以控制哪些字段参与序列化和反序列化,...
在Android开发中,Gson库是Google提供的一款强大的JSON处理工具,它允许我们将Java对象转换为对应的JSON字符串,同时也能够将JSON数据解析成相应的Java对象。这篇详细的文章将深入探讨如何利用Gson进行高效的JSON...
- **类型适配器**:通过创建`TypeAdapter`并注册到`GsonBuilder`,可以完全控制特定类型的序列化和反序列化过程。 7. **注意事项** - 当对象包含循环引用时,Gson可能会导致无限递归错误。可以使用`@Expose`注解...
6. **遍历和提取数据**:通过`getAs...()`方法获取不同类型的JsonElement并进行操作。 ```java for (Map.Entry, JsonElement> entry : jsonObject.entrySet()) { String key = entry.getKey(); JsonElement value ...
此外,它还能处理嵌套的JSON结构,以及泛型类型。 5. **类型转换**: Gson提供了一些高级特性,如`TypeToken`,用于处理不确定类型的泛型。`GsonBuilder`则允许自定义序列化和反序列化的配置,比如日期格式、字段...
6. **泛型支持**:Gson能够处理带有类型参数的类,即使这些类型信息在运行时可能丢失。 7. **配置选项**:通过`GsonBuilder`,可以设置一系列配置选项,比如是否忽略未知字段、是否启用非公共字段序列化等,以适应...