- 浏览: 1500022 次
- 性别:
- 来自: 杭州
文章分类
最新评论
-
duxingzheZet:
listview.getScrollY(); // 为啥总是0 ...
Android 记录和恢复ListView滚动的位置的两种方法 -
Escalade:
AlertDialog显示错误 Unable to add window token null is not for an application -
陌路千里:
return false即可
form表单只提交值,而不进行页面跳转 -
yubenjie:
不错,说的很全。学习了
maven用途、核心概念、用法、常用参数和命令、扩展 -
fxiaozj:
中文加数字还是不行呀
解决TextView在中文和标点存在情况下一行没显示满就换行问题
本文主要介绍在Junit单元测试中序列化时出现的java.io.NotSerializableException如何解决。
关于序列化可以参见http://trinea.iteye.com/blog/1020511
以下是Junit单测中的一段代码,主要功能是序列化一个接口变量
interface GetDataInterface extends Serializable { public Object getData(); } public void testSerializable() { GetDataInterface getData = new GetDataInterface() { private static final long serialVersionUID = 1L; @Override public Object getData() { return null; } }; ObjectOutputStream out; try { out = new ObjectOutputStream(new FileOutputStream("getData.obj")); out.writeObject(getData); out.close(); assertTrue(true); } catch (FileNotFoundException e) { e.printStackTrace(); assertFalse(true); } catch (IOException e) { e.printStackTrace(); assertFalse(true); } }
Junit运行testSerializable函数会抛出IOException异常,如下
java.io.NotSerializableException: com.*.*.*.*.Test at java.io.ObjectOutputStream.writeObject0(Unknown Source) at java.io.ObjectOutputStream.defaultWriteFields(Unknown Source) at java.io.ObjectOutputStream.writeSerialData(Unknown Source) at java.io.ObjectOutputStream.writeOrdinaryObject(Unknown Source) at java.io.ObjectOutputStream.writeObject0(Unknown Source) at java.io.ObjectOutputStream.writeObject(Unknown Source) at com.*.*.*.*.Test.testSerializable(AutoGetDataCacheTest.java:235) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) at java.lang.reflect.Method.invoke(Unknown Source) at junit.framework.TestCase.runTest(TestCase.java:154) at junit.framework.TestCase.runBare(TestCase.java:127) at junit.framework.TestResult$1.protect(TestResult.java:106) at junit.framework.TestResult.runProtected(TestResult.java:124) at junit.framework.TestResult.run(TestResult.java:109) at junit.framework.TestCase.run(TestCase.java:118) at org.eclipse.jdt.internal.junit.runner.junit3.JUnit3TestReference.run(JUnit3TestReference.java:130) at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38) at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467) at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683) at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390) at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)
即找不到序列化的对象,这种情况一般出现在序列化对象的类没有实现Serializable接口,而这里明显已经实现了,将这段函数放到main函数中执行发现正常,接着比较就能发现main函数是静态的,我们将上面的testSerializable改成静态函数
public static void testSerializable()
运行就会发现结果正常。
我们再试试对于一个类来说会怎么样
public class ClassImplSerialize implements Serializable { private static final long serialVersionUID = 88940079192401092L; } public void testSerializable() { ClassImplSerialize getData = new ClassImplSerialize(); ObjectOutputStream out; try { out = new ObjectOutputStream(new FileOutputStream("getData.obj")); out.writeObject(getData); out.close(); assertTrue(true); } catch (FileNotFoundException e) { e.printStackTrace(); assertFalse(true); } catch (IOException e) { e.printStackTrace(); assertFalse(true); } }
运行依旧会抛出上面类似的异常,这里我们将类ClassImplSerialize改为静态类,testSerializable依旧不变
public static class ClassImplSerialize implements Serializable
发现问题也可以解决。
原因:
经评论中的鼎爷指点,总结原因如下:
内部类有一个隐含的引用指向外部类,这样序列化他的时候,这个引用指向的对象必须也是可序列化的,否则就报错。(所以我们把Junit的测试用例类实现Serializable也可以解决上面的问题)
而静态内部类不包含这个引用,所以只要自己可以序列化即可。
对于静态函数能够正常通过,是因为这个内部类被静态函数引用,所以自己也相当于是静态的效果,不存在对外部类的引用了。
更多感兴趣的可以看看评论1楼到4楼
评论
5 楼
Trinea
2012-05-17
oldrat 写道
Trinea 写道
oldrat 写道
JUnit4不允许test方法为static,JUnit 3是可以。
用JUnit 3写了一下,也包含了3个Case。UT通过。
用JUnit 3写了一下,也包含了3个Case。UT通过。
soga,原来内部类有一个隐含的引用指向外部类,这样序列化他的时候,这个引用指向的对象必须也是可序列化的,否则就报错。
而静态内部类不包含这个引用,所以只要自己可以序列化即可。
那对于静态函数能够正常通过,是因为这个内部类被静态函数引用,所以自己也相当于是静态的效果,不存在对外部类的引用了?
> 那对于静态函数能够正常通过,是因为这个内部类被静态函数引用,所以自己也相当于是静态的效果,不存在对外部类的引用了?
是的。静态函数里的匿名内部类,只能成为静态类,因为静态函数没有关联this引用。非静态函数(成员函数)有关联this引用,所以可以编译成非静态的内部类。
Java应该是没有办法可以在成员函数里声明一个静态的内部类的。
有人知道 如何“可以在成员函数里声明一个静态的内部类”,如果可以,给一下代码。
函数里面声明静态内部类昨天我也试过了,不行
4 楼
oldrat
2012-05-17
Trinea 写道
oldrat 写道
JUnit4不允许test方法为static,JUnit 3是可以。
用JUnit 3写了一下,也包含了3个Case。UT通过。
用JUnit 3写了一下,也包含了3个Case。UT通过。
soga,原来内部类有一个隐含的引用指向外部类,这样序列化他的时候,这个引用指向的对象必须也是可序列化的,否则就报错。
而静态内部类不包含这个引用,所以只要自己可以序列化即可。
那对于静态函数能够正常通过,是因为这个内部类被静态函数引用,所以自己也相当于是静态的效果,不存在对外部类的引用了?
> 那对于静态函数能够正常通过,是因为这个内部类被静态函数引用,所以自己也相当于是静态的效果,不存在对外部类的引用了?
是的。静态函数里的匿名内部类,只能成为静态类,因为静态函数没有关联this引用。非静态函数(成员函数)有关联this引用,所以可以编译成非静态的内部类。
Java应该是没有办法可以在成员函数里声明一个静态的内部类的。
有人知道 如何“可以在成员函数里声明一个静态的内部类”,如果可以,给一下代码。
3 楼
Trinea
2012-05-17
oldrat 写道
JUnit4不允许test方法为static,JUnit 3是可以。
用JUnit 3写了一下,也包含了3个Case。UT通过。
用JUnit 3写了一下,也包含了3个Case。UT通过。
soga,原来内部类有一个隐含的引用指向外部类,这样序列化他的时候,这个引用指向的对象必须也是可序列化的,否则就报错。
而静态内部类不包含这个引用,所以只要自己可以序列化即可。
那对于静态函数能够正常通过,是因为这个内部类被静态函数引用,所以自己也相当于是静态的效果,不存在对外部类的引用了?
2 楼
oldrat
2012-05-17
JUnit4不允许test方法为static,JUnit 3是可以。
用JUnit 3写了一下,也包含了3个Case。UT通过。
用JUnit 3写了一下,也包含了3个Case。UT通过。
import java.io.FileOutputStream; import java.io.ObjectOutputStream; import java.io.Serializable; import junit.framework.TestCase; public class StaticClassSerializationTest extends TestCase { interface GetDataInterface extends Serializable { public Object getData(); } static GetDataInterface getData = new GetDataInterface() { private static final long serialVersionUID = 1L; public Object getData() { return null; } }; public static class ClassImplSerialize implements Serializable { private static final long serialVersionUID = 88940079192401092L; } public void testSerializable_Attribute_StaticAnonymousClass() throws Exception { ObjectOutputStream out = null; try { out = new ObjectOutputStream(new FileOutputStream("getData.obj")); out.writeObject(getData); } finally { if(null != out) { try { out.close(); } catch (Exception e) {} } } } public static void testSerializable_LocalVar_StaticAnonymousClass() throws Exception { GetDataInterface local = new GetDataInterface() { private static final long serialVersionUID = 1L; public Object getData() { return null; } }; ObjectOutputStream out = null; try { out = new ObjectOutputStream(new FileOutputStream("getData.obj")); out.writeObject(local); } finally { if (null != out) { try { out.close(); } catch (Exception e) { } } } } public void testSerializable_StaticInnerClass() throws Exception { ClassImplSerialize getData = new ClassImplSerialize(); ObjectOutputStream out = null; try { out = new ObjectOutputStream(new FileOutputStream("getData.obj")); out.writeObject(getData); } finally { if(null != out) { try { out.close(); } catch (Exception e) {} } } } }
1 楼
oldrat
2012-05-17
内部类是一个隐含的引用指向外部类。
UT失败是因为内部类不能序列化。
下面改了一下,把UT类实现Serializable,UT就都通过了。
另外可以把内部声明成static的,这样就没有隐含的指向外部类的引用,UT也可以通过。
UT失败是因为内部类不能序列化。
下面改了一下,把UT类实现Serializable,UT就都通过了。
import java.io.FileOutputStream; import java.io.ObjectOutputStream; import java.io.Serializable; import org.junit.Test; public class InnnerClassSerializationTest implements Serializable { private static final long serialVersionUID = 1L; interface GetDataInterface extends Serializable { public Object getData(); } GetDataInterface attributeData = new GetDataInterface() { private static final long serialVersionUID = 1L; public Object getData() { return null; } }; public class InnerClassSerialize implements Serializable { private static final long serialVersionUID = 88940079192401092L; } @Test public void testSerializable_Attribute_AnonymousClass() throws Exception { ObjectOutputStream out = null; try { out = new ObjectOutputStream(new FileOutputStream("getData.obj")); out.writeObject(attributeData); } finally { if (null != out) { try { out.close(); } catch (Exception e) { } } } } @Test public void testSerializable_LocalVar_AnonymousClass() throws Exception { GetDataInterface local = new GetDataInterface() { private static final long serialVersionUID = 1L; public Object getData() { return null; } }; ObjectOutputStream out = null; try { out = new ObjectOutputStream(new FileOutputStream("getData.obj")); out.writeObject(local); } finally { if (null != out) { try { out.close(); } catch (Exception e) { } } } } @Test public void testSerializable_InnerClass() throws Exception { InnerClassSerialize getData = new InnerClassSerialize(); ObjectOutputStream out = null; try { out = new ObjectOutputStream(new FileOutputStream("getData.obj")); out.writeObject(getData); } finally { if (null != out) { try { out.close(); } catch (Exception e) { } } } } }
另外可以把内部声明成static的,这样就没有隐含的指向外部类的引用,UT也可以通过。
import java.io.FileOutputStream; import java.io.ObjectOutputStream; import java.io.Serializable; import org.junit.Test; public class StaticClassSerializationTest { interface GetDataInterface extends Serializable { public Object getData(); } static GetDataInterface getData = new GetDataInterface() { private static final long serialVersionUID = 1L; public Object getData() { return null; } }; public static class ClassImplSerialize implements Serializable { private static final long serialVersionUID = 88940079192401092L; } @Test public void testSerializable_Attribute_StaticAnonymousClass() throws Exception { ObjectOutputStream out = null; try { out = new ObjectOutputStream(new FileOutputStream("getData.obj")); out.writeObject(getData); } finally { if(null != out) { try { out.close(); } catch (Exception e) {} } } } @Test public void testSerializable_StaticInnerClass() throws Exception { ClassImplSerialize getData = new ClassImplSerialize(); ObjectOutputStream out = null; try { out = new ObjectOutputStream(new FileOutputStream("getData.obj")); out.writeObject(getData); } finally { if(null != out) { try { out.close(); } catch (Exception e) {} } } } }
发表评论
-
Android 开源库获取途径整理
2014-08-20 02:14 3260最新内容请见原文: http://www.trinea.c ... -
maven常用插件配置和使用
2012-05-17 20:14 6310最新内容见:Maven常用插件配置和使用 本文主要是 ... -
总结的一些Java公用函数库
2012-06-18 15:41 9117最新内容建议直接访问原文:Android常用的工具类 ... -
PreloadDataCache支持预取的数据缓存,使用简单,支持多种缓存算法,支持不同网络类型,扩展性强
2012-06-18 15:44 4335最新内容建议直接访 ... -
异常处理的最佳实践[转载]
2012-05-15 17:01 1545之前一直对异常处理比较疑惑,通常有点随心所欲而没有规范统一的处 ... -
重构#读书笔记#
2012-03-31 10:06 01、要在工程已开始就有很好的设计在不改动几乎不可能,因为代码不 ... -
设计模式
2012-03-12 00:11 0设计模式 Gof的设计模式 -
Java Semaphore用法
2012-03-09 14:15 0参考:http://comeonbabye.ite ... -
大话设计模式 #笔记#1
2012-01-31 23:51 0软件设计原则 1、单一职责原则 2、开放封闭原则 3、依 ... -
eclipse中查看Java源代码
2012-01-16 23:25 6674在eclipse中对于自己的代码可以通过按住Ctrl的同时单击 ... -
多线程使用中的一些好习惯
2012-01-17 00:24 2633本文主要介绍个人在多线程使用和调优中总结一些线程使用比较好的习 ... -
ThreadLocal 介绍及使用举例
2012-01-05 21:41 0参考: http://lavasoft.blog.51cto ... -
腾讯微博java(android) api
2011-12-15 00:50 12084由于现在腾讯微博提 ... -
java CyclicBarrier CountDownLatch
2011-12-07 23:30 0http://www.iteye.com/topic/7130 ... -
Hudson 插件编写
2011-12-10 00:10 2772Hudson是一个开源的持续集成工具,由于其强大的扩展性(插件 ... -
maven用途、核心概念、用法、常用参数和命令、扩展
2011-12-05 19:15 65938最新内容见:Maven介绍,包括作用、核心概念、用法、常用 ... -
java 利用spring JavaMailSenderImpl发送邮件,支持普通文本、附件、html、velocity模板
2011-11-25 20:59 23833本文主要介绍利用JavaMa ... -
windows机器性能监控
2011-11-24 18:55 1853主要介绍一般windows系统监控,以及Windows Ser ... -
Junit单元测试中获得spring bean
2011-11-23 11:44 14132主要介绍单元测试中获得bean的三种方法,以及各自的优劣。其 ... -
对象数组或list排序及Collections排序原理
2011-11-09 22:42 27803常需要对list进行排序 ...
相关推荐
在java中使用 junit单元测试,eclipse 使用Junit为java程序做单元测试,图文教程,非常使用
Junit单元测试Junit单元测试Junit单元测试Junit单元测试
Junit单元测试Junit单元测试Junit单元测试Junit单元测试
《单元测试之道Java版:使用JUnit》PDF 下载
简单介绍了Junit的安装过程与实例应用。应用的问题是软件测试中的佣兵问题,整个文档中有代码及测试结果,可以更好地帮助学生了解Junit单元测试中的作用。
单元测试之道(Java):使用JUnit进行单元测试。单元测试是提高代码质量的有效手段,但大部分开发人员由于种种原因都不乐意进行单元测试。
Junit java单元测试内部机制解析
junit测试测试junit测试测试junit测试测试junit测试测试
junit单元测试junit单元测试junit单元测试
单元测试之道Java版——使用Junit,不错的学习测试的教材
Junit单元测试指南 Junit单元测试指南 Junit单元测试指南 Junit单元测试指南 Junit单元测试指南 Junit单元测试指南
JUnit测试代码示例,JUnit3的代码示例。
junit测试 test txt file
本代码属于Java练习基本篇,主要写了关于Java单元格测试的一些相关内容,仅供初学者参考借鉴,因为写的时间久了,忘了当时的思路,有需要的同学请耐下心来仔细翻阅,不足之处请海涵
多数Java的开发环境都已经集成了JUnit作为单元测试的工具。 [1] JUnit是由 Erich Gamma 和 Kent Beck 编写的一个回归测试框架(regression testing framework)。Junit测试是程序员测试,即所谓白盒测试,因为...
Junit 单元测试 包括Spring Struts 两个模块的测试案例。附源码
单元测试之道Java版使用JUnit,是关于java的单元测试的。
junit4 jar包 Java单元测试框架绿色免费版.zip
在Eclipse中使用JUnit4进行单元测试!
软件测试 JUnit NUnit测试 C# java