java 中的克隆
来源:互联网 发布:手机医用软件 编辑:程序博客网 时间:2024/05/22 13:21
大家好:今天是我第一次发博客,主要介绍一下java中克隆的有关知识,这和C++中的不一样。
首先看一段程序,以及运行结果。
import java.awt.Color;public class Cfc1{public static void main(String args[]){Cat cat1=new Cat("Java",12,21,Color.black);Cat cat2=new Cat("C++",12,21,Color.white);Cat cat3=new Cat("C#",12,21,Color.black);System.out.println("Before");System.out.println("猫咪1号:"+cat1);System.out.println("猫咪2号:"+cat2);System.out.println("猫咪3号:"+cat3);cat2=cat1;System.out.println("Now");cat2.setInfo();System.out.println("猫咪1号:"+cat1);System.out.println("猫咪2号:"+cat2);System.out.println("猫咪3号:"+cat3);}}class Cat{private String name;private int age;private double weight;private Color color;public Cat(String name,int age,double weight,Color color){this.name=name;this.age=age;this.weight=weight;this.color=color;}public void setInfo(){this.name="VB";this.age=13;this.weight=23;this.color=Color.BLUE;}public boolean equals(Cat cat){if(this==cat){return true;}else{return false;}}public String toString(){StringBuffer sb=new StringBuffer();sb.append("name="+name+"\n");sb.append("age="+age+"\n");sb.append("weight="+weight+"\n");sb.append("Color="+color+"\n");return sb.toString();}}
结果如下:
Before
猫咪1号:name=Java
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
猫咪2号:name=C++
age=12
weight=21.0
Color=java.awt.Color[r=255,g=255,b=255]
猫咪3号:name=C#
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
Now
猫咪1号:name=VB
age=13
weight=23.0
Color=java.awt.Color[r=0,g=0,b=255]
猫咪2号:name=VB
age=13
weight=23.0
Color=java.awt.Color[r=0,g=0,b=255]
猫咪3号:name=C#
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
代码中的cat2.setInfo();明明是修改cat2的,为什么修改cat2之后cat1也改了?
那是因为这里的cat1 ,cat2,cat3,相当于C++中的指针(java 中“没有“指针,只不过是把指针操作封装了,其实是有的这里的cat1 ,cat2,cat3,就相当于地址)
那要克隆的话怎么办呢?
请再看如下代码:
import java.awt.Color;public class Cfc2{public static void main(String args[]){Cat cat1=new Cat("Java",12,21,Color.black);Cat cat2=new Cat("C++",12,21,Color.white);Cat cat3=new Cat("C#",12,21,Color.black);System.out.println("Before");System.out.println("猫咪1号:"+cat1);System.out.println("猫咪2号:"+cat2);System.out.println("猫咪3号:"+cat3);cat2=cat1.clone();System.out.println("Now");cat2.setInfo();System.out.println("猫咪1号:"+cat1);System.out.println("猫咪2号:"+cat2);System.out.println("猫咪3号:"+cat3);}}class Cat implements Cloneable{private String name;private int age;private double weight;private Color color;public Cat(String name,int age,double weight,Color color){this.name=name;this.age=age;this.weight=weight;this.color=color;}public void setInfo(){this.name="VB";this.age=13;this.weight=23;this.color=Color.BLUE;}public boolean equals(Cat cat){if(this==cat){return true;}else{return false;}}public String toString(){StringBuffer sb=new StringBuffer();sb.append("name="+name+"\n");sb.append("age="+age+"\n");sb.append("weight="+weight+"\n");sb.append("Color="+color+"\n");return sb.toString();}public Cat clone(){Cat cat=null;try{cat=(Cat)super.clone();}catch(CloneNotSupportedException e){e.printStackTrace();}return cat;}}
运行结果如下:
Before
猫咪1号:name=Java
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
猫咪2号:name=C++
age=12
weight=21.0
Color=java.awt.Color[r=255,g=255,b=255]
猫咪3号:name=C#
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
Now
猫咪1号:name=Java
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
猫咪2号:name=VB
age=13
weight=23.0
Color=java.awt.Color[r=0,g=0,b=255]
猫咪3号:name=C#
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
看!!! 这次cat1没有被修改吧,原因就在于cat2=cat1.clone(); 以及class Cat implements Cloneable cat2相当于拥有了另一块同cat1内容一样的空间 而之前
的那个例子 cat1,cat2是共同指向一个空间,所以cat2.setInfo();之后,cat1也被改了。
可是,再看看下面的程序以及运行结果,你会发现又有问题了。
import java.awt.Color;public class Cfc3{public static void main(String args[]){Cat cat1=new Cat("Java",12,21,Color.black,new LikeFood("fish","meet"));Cat cat2=new Cat("C++",12,21,Color.white,new LikeFood("firut","vegtable"));Cat cat3=new Cat("C#",12,21,Color.black,new LikeFood("banana","apple"));System.out.println("Before");System.out.println("猫咪1号:"+cat1);System.out.println("猫咪2号:"+cat2);System.out.println("猫咪3号:"+cat3);cat2=cat1.clone();System.out.println("Now");cat2.setInfo();System.out.println("猫咪1号:"+cat1);System.out.println("猫咪2号:"+cat2);System.out.println("猫咪3号:"+cat3);}}class Cat implements Cloneable{private String name;private int age;private double weight;private Color color;private LikeFood lf;public Cat(String name,int age,double weight,Color color,LikeFood lf){this.name=name;this.age=age;this.weight=weight;this.color=color;this.lf=lf;}public void setInfo(){this.name="VB";this.age=13;this.weight=23;this.color=Color.BLUE;this.lf.setInfo();}public String toString(){StringBuffer sb=new StringBuffer();sb.append("name="+name+"\n");sb.append("age="+age+"\n");sb.append("weight="+weight+"\n");sb.append("Color="+color+"\n");sb.append("LikeFood::"+lf+"\n");return sb.toString();}public Cat clone(){Cat cat=null;try{cat=(Cat)super.clone();}catch(CloneNotSupportedException e){e.printStackTrace();}return cat;}}class LikeFood{private String firstfood;private String secondfood;public LikeFood(String firstfood,String secondfood){this.firstfood=firstfood;this.secondfood=secondfood;}public String toString(){StringBuffer sb=new StringBuffer();sb.append("firstfood="+firstfood+" secondfood="+secondfood);return sb.toString();}public void setInfo(){this.firstfood="sheet";this.secondfood="urine";}}
运行结果如下:
Before
猫咪1号:name=Java
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
LikeFood::firstfood=fish secondfood=meet
猫咪2号:name=C++
age=12
weight=21.0
Color=java.awt.Color[r=255,g=255,b=255]
LikeFood::firstfood=firut secondfood=vegtable
猫咪3号:name=C#
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
LikeFood::firstfood=banana secondfood=apple
Now
猫咪1号:name=Java
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
LikeFood::firstfood=sheet secondfood=urine
猫咪2号:name=VB
age=13
weight=23.0
Color=java.awt.Color[r=0,g=0,b=255]
LikeFood::firstfood=sheet secondfood=urine
猫咪3号:name=C#
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
LikeFood::firstfood=banana secondfood=apple
这次有cat2=cat1.clone(); 怎么cat1有一部分被改变了 ,另一部分没有被改变???
我们还可以发现被改变的不是基本数据类型,而没改的是基本数据类型。
这说明当执行cat2=cat1.clone();之后,对于基本数据类型,是真正意义上的克隆,而对于类变量,不是真正的克隆
还是cat1,cat2共同指向cat1的private LikeFood lf; 所以cat2.setInfo();之后,对于类数据类型的那一部分,cat1` 与cat2都改了。
以下是最终的正确完整的程序:
import java.awt.Color;public class Cfc4{public static void main(String args[]){Cat cat1=new Cat("Java",12,21,Color.black,new LikeFood("fish","meet"));Cat cat2=new Cat("C++",12,21,Color.white,new LikeFood("firut","vegtable"));Cat cat3=new Cat("C#",12,21,Color.black,new LikeFood("banana","apple"));System.out.println("Before");System.out.println("猫咪1号:"+cat1);System.out.println("猫咪2号:"+cat2);System.out.println("猫咪3号:"+cat3);cat2=cat1.clone();cat2.lf=cat2.lf.clone();System.out.println("Now");cat2.setInfo();System.out.println("猫咪1号:"+cat1);System.out.println("猫咪2号:"+cat2);System.out.println("猫咪3号:"+cat3);}}class Cat implements Cloneable{private String name;private int age;private double weight;private Color color;public LikeFood lf;public Cat(String name,int age,double weight,Color color,LikeFood lf){this.name=name;this.age=age;this.weight=weight;this.color=color;this.lf=lf;}public void setInfo(){this.name="VB";this.age=13;this.weight=23;this.color=Color.BLUE;this.lf.setInfo();}public String toString(){StringBuffer sb=new StringBuffer();sb.append("name="+name+"\n");sb.append("age="+age+"\n");sb.append("weight="+weight+"\n");sb.append("Color="+color+"\n");sb.append("LikeFood::"+lf+"\n");return sb.toString();}public Cat clone(){Cat cat=null;try{cat=(Cat)super.clone();}catch(CloneNotSupportedException e){e.printStackTrace();}return cat;}}class LikeFood implements Cloneable{private String firstfood;private String secondfood;public LikeFood(String firstfood,String secondfood){this.firstfood=firstfood;this.secondfood=secondfood;}public String toString(){StringBuffer sb=new StringBuffer();sb.append("firstfood="+firstfood+" secondfood="+secondfood);return sb.toString();}public void setInfo(){this.firstfood="sheet";this.secondfood="urine";}public LikeFood clone(){LikeFood lf=null;try{lf=(LikeFood)super.clone();}catch(CloneNotSupportedException e){e.printStackTrace();}return lf;}}
结果如下:
Before
猫咪1号:name=Java
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
LikeFood::firstfood=fish secondfood=meet
猫咪2号:name=C++
age=12
weight=21.0
Color=java.awt.Color[r=255,g=255,b=255]
LikeFood::firstfood=firut secondfood=vegtable
猫咪3号:name=C#
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
LikeFood::firstfood=banana secondfood=apple
Now
猫咪1号:name=Java
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
LikeFood::firstfood=fish secondfood=meet
猫咪2号:name=VB
age=13
weight=23.0
Color=java.awt.Color[r=0,g=0,b=255]
LikeFood::firstfood=sheet secondfood=urine
猫咪3号:name=C#
age=12
weight=21.0
Color=java.awt.Color[r=0,g=0,b=0]
LikeFood::firstfood=banana secondfood=apple
看!!!!这下子好了吧!!!
总结::Cfc1中克隆出现了问题,Cfc2解决了(这是Cfc1,Cfc2里面的成员变量里没有类这样的数据类型)
Cfc3中又出现了问题原因在于成员变量中加入了类这样的数据类型,对于这样的类,也要implements Cloneable
才行,所以Cfc4出现了,解决了比较完整的问题
当然对于对象的克隆也可以通过序列化的方法解决,过程会简单一点,但是序列化的方法效率没有本文的方法好
- java中的克隆
- java中的对象克隆
- java中的克隆
- 关于java中的克隆
- java 中的克隆
- Java中的克隆
- Java中的对象克隆
- java中的深浅克隆
- Java中的克隆
- Java中的深浅克隆
- java中的浅克隆
- java中的克隆问题
- Java中的对象克隆
- Java中的克隆
- java中的深克隆和浅克隆
- java中的深克隆浅克隆介绍
- JAVA中的深克隆和浅克隆
- Java中的浅克隆和深克隆
- AsyncTask使用注意事项
- (部分已做修改)C#访问远程主机资源的方法---用户模拟角色类
- 织网的日子里——第一章:TCP时间获取之客户端和服务器端程序
- 块设备驱动 block_device_operations结构体 主要成员函数分析
- 随笔
- java 中的克隆
- 内存
- “ORA-12541:TNS:无监听程序”错误
- Android:HandlerThread
- 压力测试工具WCAT
- jena中关于本体操作的几个代码。(自己看的笔记)
- 详解struts2中struts.properties
- {软件工程}之逆向工程
- IDE的本质