java序列化深克隆

开发人员经常依靠3d方库来避免重新发明轮子,尤其是在Java世界中,Apache和Spring这样的项目如此盛行。 在处理这些框架时,我们通常很少或根本无法控制其类的行为。

这有时会导致问题。 例如,如果您想深克隆一个不提供合适克隆方法的对象,除了编写大量代码之外,您还有什么选择?

通过序列化克隆

最简单的方法是通过利用对象可序列化进行克隆。 Apache Commons提供了一种执行此操作的方法,但是为了完整起见,下面也是您自己执行此操作的代码。

@SuppressWarnings("unchecked")
public static  T cloneThroughSerialize(T t) throws Exception {ByteArrayOutputStream bos = new ByteArrayOutputStream();serializeToOutputStream(t, bos);byte[] bytes = bos.toByteArray();ObjectInputStream ois = new ObjectInputStream(new ByteArrayInputStream(bytes));return (T)ois.readObject();
}private static void serializeToOutputStream(Serializable ser, OutputStream os)throws IOException {ObjectOutputStream oos = null;try {oos = new ObjectOutputStream(os);oos.writeObject(ser);oos.flush();} finally {oos.close();}
}// using our custom method
Object cloned = cloneThroughSerialize (someObject);// or with Apache Commons
cloned = org.apache.commons.lang. SerializationUtils.clone(someObject);

但是,如果我们要克隆的类不是可序列化的,并且我们无法控制源代码或者无法将其设置为可序列化该怎么办?

选项1 – Java深度克隆库

有一个不错的小程序库,它可以深度克隆几乎所有Java对象- 克隆 。 它利用Java的出色反射功能来提供优化的对象的深克隆版本。

Cloner cloner=new Cloner();
Object cloned = cloner.deepClone(someObject);

如您所见,它非常简单有效,并且需要最少的代码。 除了这个简单的示例,它还具有一些更高级的功能,您可以在此处查看 。

选项2 – JSON克隆

如果我们无法将新库引入我们的代码库,该怎么办? 我们中有些人处理批准程序以引入新的库,对于一个简单的用例,可能不值得。

好吧,只要我们有某种方式可以序列化和还原对象,就可以进行深层复制。 JSON通常被使用,因此它是一个很好的选择,因为我们大多数人都使用一个或另一个JSON库。

Java中的大多数JSON库都可以有效地序列化任何POJO,而无需任何配置或映射。 这意味着,如果您具有JSON库并且不能或不会引入更多库来提供深度克隆,则可以利用现有的JSON库来获得相同的效果。 请注意,此方法将比其他方法慢,但是对于绝大多数应用程序,这不会引起任何性能问题。

以下是使用GSON库的示例。

@SuppressWarnings("unchecked")
public static  T cloneThroughJson(T t) {Gson gson = new Gson();String json = gson.toJson(t);return (T) gson.fromJson(json, t.getClass());
}
// ...
Object cloned = cloneThroughJson(someObject);

请注意,仅当复制的对象具有默认的无参数构造函数时,这才可能起作用。 对于GSON,您可以使用实例创建者来解决此问题。 其他框架具有类似的概念,因此如果遇到无法修改的类且没有默认构造函数的问题,则可以使用该框架。


结论

我建议做的一件事是,对于需要克隆的任何类,都应该添加一些单元测试,以确保一切正常。 这可以防止对类的更改(例如,升级库版本)在您不知情的情况下破坏应用程序,尤其是在您设置了持续集成环境的情况下。

我概述了几种在没有任何自定义代码的情况下克隆对象的方法。 如果您使用其他任何方法获得相同的结果,请分享。

参考: Carfey Software Blog上的JCG合作伙伴 Craig Flichel从Java轻松深度克隆了Java中的可序列化和不可序列化的对象 。

相关文章 :

  • Java最佳实践–高性能序列化
  • 使用Gson教程进行Android JSON解析
  • 在您的GWT应用程序中添加JSON功能
  • Java 7功能概述
  • Java Code Geeks编写的Java示例和代码段–正式发布

翻译自: https://www.javacodegeeks.com/2011/12/cloning-of-serializable-and-non.html

java序列化深克隆

java序列化深克隆_克隆可序列化和不可序列化的Java对象相关推荐

  1. java序列化深克隆_如何在内存序列化中使用Java深克隆对象

    java序列化深克隆 在我以前的文章中,我解释了深度克隆和浅层克隆之间的区别 , 以及复制构造函数和防御性复制方法比默认的Java克隆如何更好. 使用复制构造函数和防御性复制方法进行的Java对象克隆 ...

  2. java面试题_阿里大厂流出的数百道 Java 经典面试题

    BAT 常问的 Java基础39道常见面试题 1.八种基本数据类型的大小,以及他们的封装类 2.引用数据类型 3.Switch能否用string做参数 4.equals与==的区别 5.自动装箱,常量 ...

  3. java输入输出流_金九银十准备季:Java异常+Java IO与NIO面试题(含答案)

    写在前面:2020年面试必备的Java后端进阶面试题总结了一份复习指南在Github上,内容详细,图文并茂,有需要学习的朋友可以Star一下! GitHub地址:abel-max/Java-Study ...

  4. java循环输入_【图文+视频新手也友好】Java一维数组详细讲解(内含练习题答案+详解彩蛋喔~)...

    [新手友好型视频+图文] 全面讲解Java一维数组(内含带答案和讲解的练习题彩蛋喔) 看完即上手!更有详解版练习题来帮你加深印象~~ 一.视频讲解 一维数组详解https://www.zhihu.co ...

  5. java jni编译_从源码编译Android系统的Java类库和JNI动态库的方法

    利用源码编译Android系统Java类库 1.编写Java项目和Android.mk文件 ├── Android.mk └── src └── com └── lhw └── framework └ ...

  6. java内置_自包含的应用程序,内置Java

    我已经看过几篇在Java 9中简要提到自包含应用程序的在线演示文稿,但我有一个问题需要我解决. 使用新模块系统,您现在只允许包含运行应用程序所需的最少代码.但是,希望运行应用程序的系统是否仍需要JRE ...

  7. java ui调试_如何使用 IBM i System Debugger 调试 Java 程序

    当在 IBM i 上使用 Java 时,您可以使用 Qshell Interpreter 或者 CL 命令提供的 Java tools,在 Qshell 环境和 IBM i 环境上进行与 Java 开 ...

  8. java idea 模块_使用IntelliJ IDEA搭建多maven模块JAVA项目

    一.新建项目和模块 步骤: 1. 新建一个项目,因为maven管理jar包非常方便,故此处建立一个maven项目:New Project->Maven->(Create from arch ...

  9. java 编写代码_如果您在2016年编写过Java代码-这是您不容错过的趋势

    java 编写代码 2016年最有趣的Java相关主题 关于代码,有很多热门话题,而要跟上所有事情,这是一项全职的工作. 如果您想知道如何从谷壳中分离出小麦,我们已经为您完成了工作. 在下面的文章中, ...

最新文章

  1. 中国人长期“霸榜”GitHub,国外开发者发文控诉
  2. 等差数列末项_等差数列末项(第n项)公式
  3. Nature重磅:管轶等发现穿山甲是SARS-CoV-2的中间宿主
  4. DllRegisterServer的调用失败
  5. 【算法】算法秋招个人总结
  6. JAVA语言程序设计课后习题----第四单元解析(仅供参考)
  7. Slony-I双机备份
  8. 计算机安全基础:认证技术知识笔记
  9. 让 .Net 更方便的导入导出Excel
  10. spring-junit4_基于Spring的应用程序-迁移到Junit 5
  11. 利用反射和xml配置文件手写一个小型的框架
  12. jquery工具箱旋转动画效果
  13. Pycharm中无法导入各种Python模块,pip不能更新的解决办法
  14. windows2019迁移FSMO
  15. 2018/12/06 L1-022 L1-022 奇偶分家 Java
  16. linux c 语言编程如何把串口字符串数据写到txt文件中_C 语言简单编程速成 | Linux 中国...
  17. psql 命令行使用
  18. 【最长上升子序列】HDU 1087——Super Jumping! Jumping! Jumping!
  19. 【C语言编程】无重复数字的三位数
  20. jsonobject中getkey_获取JSON中所有的KEY

热门文章

  1. bootstrap组件
  2. 基本数据类型、包装类、String三者之间的相互转换
  3. 蓝桥杯JAVA省赛2013-----B------4(黄金连分数)
  4. System.err: java.net.UnknownServiceException: CLEARTEXT communication to 192.168.43.172 not permitte
  5. 用limit 实现java的简单分页
  6. 2015c语言9月答案,2015年9月计算机二级C语言预测题答案
  7. 编程猜单词游戏python_Python实现简单的猜单词小游戏
  8. MySQL优化(二):索引的类型、匹配原则、创建原则
  9. elk 日志管理_具有ELK的APIGEE API网关日志管理(弹性搜索,Logstash和Kibana)
  10. gradle项目 构建_使用Gradle构建Monorepo项目