Java Object 对象拷贝
2016-07-12 16:22
393 查看
Java Object 对象拷贝
@author ixenosJAVA 对象拷贝
Java里的clone分为:1.浅拷贝:浅复制仅仅复制所考虑的对象,而不复制它所引用的对象,Object类里的clone方法是浅拷贝
2.深拷贝:深复制把要复制的对象及其所引用的对象都复制了一遍
3.序列化深拷贝:把对象写到流里的过程是序列化(Serilization)过程,而把对象从流中读出来的过程则叫做反序列化(Deserialization)过程。应当指出的是,写在流里的是对象的一个拷贝,而原对象仍然存在于JVM里面,利用这个特性,可以做深拷贝
深拷贝时必须要遵循下面三点:
1.在派生类中覆盖基类的clone()方法,并声明为public(Object类中的clone()方法为protected的)
2.在派生类的clone()方法中,调用super.clone()
3.在派生类中实现Cloneable接口
示例
浅拷贝的例子:import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.ObjectInputStream; import java.io.ObjectOutputStream; import java.io.Serializable; //利用序列化来做深复制 //深clone public class DeepCloneTest { public static void main(String[] args) throws Exception { // teacher对象将不被clone出来的Student对象共享. Teacher teacher = new Teacher(); teacher.setAge(40); teacher.setName("Teacher zhang"); Student student1 = new Student(); student1.setAge(20); student1.setName("zhangsan"); student1.setTeacher(teacher); // 复制出来一个对象student2 Student student2 = (Student) student1.deepCopy(); System.out.println(student2.getAge()); System.out.println(student2.getName()); System.out.println("~~~~~~~~~~~~~~~~~~~~~~"); System.out.println(student1.getTeacher().getAge()); System.out.println(student1.getTeacher().getName()); // 修改student2的引用对象 student2.getTeacher().setAge(50); student2.getTeacher().setName("Teacher Li"); System.out.println("~~~~~~~~~~~~~~~~~~~~~~"); System.out.println(student1.getTeacher().getAge()); System.out.println(student1.getTeacher().getName()); } } class Teacher implements Serializable { private static final long serialVersionUID = -8834559347461591191L; public int age; public String name; public int getAge() { return age; } public void setAge(int age) { this.age = age; } public String getName() { return name; } public void setName(String name) { this.name = name; } } class Student implements Serializable { // serialVersionUID // 如果你的对象序列化后存到硬盘上面后,可是后来你却更改了类的field(增加或减少或改名),当你反序列化时,就会出现Exception的,这样就会造成不兼容性的问题。 // 但当serialVersionUID相同时,它就会将不一样的field以type的缺省值赋值(如int型的是0,String型的是null等),这个可以避开不兼容性的问题。所以最好给serialVersionUID赋值 private static final long serialVersionUID = 7991552226614088458L; public int age; public String name; public Teacher teacher; public int getAge() { return age; } public void setAge(int age) { this.age = age; } public String getName() { return name; } public void setName(String name) { this.name = name; } public Teacher getTeacher() { return teacher; } public void setTeacher(Teacher teacher) { this.teacher = teacher; } /** * 因为对象序列化会自然地对对象深拷贝,再利用“序列化-反序列化”读出 */ public Object deepCopy() throws Exception { // 将该对象序列化成流,因为写在流里的是对象的一个拷贝,而原对象仍然存在于JVM里面。所以利用这个特性可以实现对象的深拷贝 ByteArrayOutputStream bos = new ByteArrayOutputStream(); ObjectOutputStream oos = new ObjectOutputStream(bos); //this很关键,引用当前对象,当然,这是值传递 oos.writeObject(this); // 将流序列化成对象 ByteArrayInputStream bis = new ByteArrayInputStream(bos.toByteArray()); ObjectInputStream ois = new ObjectInputStream(bis); return ois.readObject(); } } 输出结果为: 20 zhangsan ~~~~~~~~~~~~~~~~~~~~~~ 40 Teacher zhang ~~~~~~~~~~~~~~~~~~~~~~ 40 Teacher zhang
View Code
相关文章推荐
- Objective-C(一,导言)
- childobjects方法
- Objective-C 入门教程(一)
- 17SWFObject使用
- 法线从object space到eye space的转换((normal matrix)
- Objective-C开发编码规范:4大方面解决开发中的规范性问题
- java.lang.String cannot be cast to [Ljava.lang.Object
- Objective-C Runtime
- Objective-C 消息发送与转发机制原理
- 内存管理基本原理
- bean的加载(九)记录创建bean的ObjectFactory
- Object Animator和Tween Animation
- List<Object>及 JSONArray互转工具方法
- networkx库:AttributeError: 'module' object has no attribute 'graphviz_layout'
- Null Object Design Pattern (Python recipe)
- runtime的那点事儿(二)消息机制
- 一个Object带多个材质如何在程序中更换
- XXX_$$_javassist_5 cannot be cast to javassist.util.proxy.ProxyObject
- 获取类对象(Retrieving Class Objects)
- 详将JSONObject与JSONArray