2011年12月28日 星期三

[JAVA]Object-物件的複製使用clone()

[JAVA]Object-物件的複製使用clone()

要使用clone(),需要實作介面Cloneable。

Object 類別本身不實作介面 Cloneable,所以在類別為 Object 的物件上調用 clone 方法將會導致在運行時拋出異常。

CloneNotSupportedException - 
如果物件的類別不支持 Cloneable 介面,則覆寫 clone 方法的子類別也會拋出此異常,以指示無法複製某個實例。

Object 類別的 clone 方法執行特定的複製操作。
首先,如果此物件的類別不能實作介面 Cloneable,
則會拋出 CloneNotSupportedException。
注意,所有的陣列都被視為實作介面 Cloneable。
否則,此方法會創建此物件的類別的一個新實例,並像通過分派那樣,
嚴格使用此物件相應欄位的內容初始化該物件的所有欄位;
這些欄位的內容沒有被自我複製。
所以,此方法執行的是該物件的「淺表複製」,而不「深層複製」操作。

測試:
一般用法:(淺表複製)
package com.test;

public class TestClone implements Cloneable {
 public static final  int i=1;

 @Override
 public Object clone() throws CloneNotSupportedException {
  return super.clone();
 }
 
 public static void main(String[] args) {
  
  try {
   TestClone t = new TestClone();
   //使用clone
   TestClone t1 = (TestClone) t.clone();
   //顯示記憶體位置
   System.out.println(t);
   //com.test.TestClone@150bd4d
   System.out.println(t1);
   //com.test.TestClone@1bc4459
   //位置是不一樣了,是不同的物件
   
   //陣列會自動implements Cloneable
   //所以會有clone的功能
   int i[] = {1,2,5,8,8,8};
   int a[]=i.clone();
   System.out.println(i.equals(a));
   //false
   System.out.println(a[2]);
   //5
  }
  catch (CloneNotSupportedException e) {
   e.printStackTrace();
  }
 }
}


進階用法:( 深層複製 )
例:
用一般的用法:
package com.test;

import java.util.ArrayList;

public class TestCloneAdvanced implements Cloneable{

 private int   i;
 private ArrayList arrayList;

 @Override
 public String toString() {
  return "i=" + i + ",arrayList=" + arrayList;
 }

 public static void main(String[] args) {
  TestCloneAdvanced clone1 = new TestCloneAdvanced();
  clone1.i = 3;
  clone1.arrayList = new ArrayList();
  clone1.arrayList.add("value 1");
  TestCloneAdvanced clone2 = null;
  try {
   clone2 = (TestCloneAdvanced) clone1.clone();
  }
  catch (CloneNotSupportedException e) {
   e.printStackTrace();
  }
  System.out.println("複製物件後,顯示結果:");
  System.out.println("clone1:" + clone1);
  System.out.println("clone2:" + clone2);
  System.out.println("將clone1改變值後,顯示結果:");
  clone1.i = 5;
  clone1.arrayList.add("value 2");
  System.out.println("clone1:" + clone1);
  System.out.println("clone2:" + clone2);
  System.out.println("將clone1改變值後,clone2的arrayList的值也會改");
  System.out.println("因為arrayList物件沒有複製");
  System.out.println("clone1.arrayList==clone2.arrayList?" +
                     (clone1.arrayList == clone2.arrayList));
 }

}
結果在物件裡的物件,無法複製。


結決方法:Override clone
例:
package com.test;

import java.util.ArrayList;

public class TestCloneAdvanced1 implements Cloneable {

 private int   i;
 private ArrayList arrayList;

 @Override
 public String toString() {
  return "i=" + i + ",arrayList=" + arrayList;
 }

 @Override
 public Object clone() throws CloneNotSupportedException {
  TestCloneAdvanced1 clone = (TestCloneAdvanced1) super.clone();
  clone.arrayList = (ArrayList) this.arrayList.clone();
  return clone;
 }

 public static void main(String[] args) {
  TestCloneAdvanced1 clone1 = new TestCloneAdvanced1();
  clone1.i = 3;
  clone1.arrayList = new ArrayList();
  clone1.arrayList.add("value 1");
  TestCloneAdvanced1 clone2 = null;
  try {
   clone2 = (TestCloneAdvanced1) clone1.clone();
  }
  catch (CloneNotSupportedException e) {
   e.printStackTrace();
  }
  System.out.println("複製物件後,顯示結果:");
  System.out.println("clone1:" + clone1);
  System.out.println("clone2:" + clone2);
  System.out.println("將clone1改變值後,顯示結果:");
  clone1.i = 5;
  clone1.arrayList.add("value 2");
  System.out.println("clone1:" + clone1);
  System.out.println("clone2:" + clone2);
  System.out.println("將clone1改變值後,clone2的arrayList的值不會改了");
  System.out.println("clone1.arrayList==clone2.arrayList?" + 
                      (clone1.arrayList == clone2.arrayList));
 }

}

結果:



進階參考網站:

小妖與鴨居的家














其它文章

沒有留言:

張貼留言

標籤

Oracle (150) Oracle DB (144) Oracle_DB (143) Oracle SQL (135) JAVA (84) css-基本類 (65) MySQL (59) CSS Selector (58) jQuery (49) JavaScript-基本類 (39) Spring Boot (38) JavaScript (37) JavaScript HTML DOM (37) JavaScript-HTML_DOM (36) CSS3 (30) JAVA-基本類 (28) jQuery UI (27) Apache (23) Oracle GROUP BY (20) datepicker (20) Android (18) Oracle Date (17) c (17) JAVA-lang套件 (16) Linux (16) Oracle Sub Query (16) Spring-基本類 (16) jQuery-基本類 (16) MySQL-進階系列教學 (15) Android基本類 (14) Grails (14) Oracle join (14) SQLite (13) Spring (13) WIN7-基本類 (13) grails-基本類 (13) linux cent os (13) CKEditor (12) JAVA-流程控制類 (12) JAVA_Spring (12) PHP (11) Spring MVC (11) MySQL-基本系列教學 (10) Notepad (10) Notepad++ (10) SQLite for java (10) Windows (10) c/c++ (10) eclipse (9) jQuery-Selector (9) sqldeveloper (9) DB_Toad (8) JAVA_IDE_Eclipse (8) JavaScript-String類 (8) MySQL DB Toad (8) MySQL-DATE相關 (8) MySQL-函式相關 (8) Spring Bean (8) Android Studio (7) HTML5 (7) Hibernate (7) JAVA-OCWCD (7) JavaScript-陣列類 (7) Docker (6) JAVA-程式分享 (6) JAVA.util套件 (6) JavaScript-數學類 (6) MinGw (6) MySQL-其它類 (6) Servlet (6) centos (6) Apache_Tomcat (5) Apache套件_POI (5) CSS (5) JavaScript-Date物件 (5) JavaScript-其它類 (5) PostgreSQL (5) httpd (5) log4j (5) 基本資訊 (5) 開發工具 (5) CSS Properties (4) Dev-C++ (4) IntelliJ IDEA (4) Oracle DDL (4) Sublime (4) TortoiseSVN (4) apache_Maven (4) Android NDK (3) Eclipse IDE for C/C++ (3) Hibernate-基本類 (3) JAVA-問題 (3) JAVA-綀習分享 (3) JVM (3) Linux 指令 (3) Proxy Server (3) Spring Mobile (3) Spring web (3) Squid (3) VirtualBox (3) maven (3) zk (3) 生活其它 (3) Bootstrap (2) Filter (2) JAVA_IO (2) JAVA_其它_itext套件 (2) JBoss-問題 (2) JSP (2) Jboss (2) Listener (2) MySQL-語法快速查詢 (2) Spring AOP (2) Spring Batch (2) Spring Boot Actuator (2) Spring i18n (2) Subversive (2) Tomcat 8 (2) UML (2) WebJars (2) WinMerge (2) c++ (2) c語言綀習題 (2) jQuery Mobile (2) jQuery-事件處理 (2) jQuery-套件類 (2) putty (2) svn (2) weblogic (2) Apache_JMeter (1) Apache套件_BeanUtils (1) Apache套件_StringUtils (1) Base64 (1) Google API (1) HTML5-基本類 (1) Heap (1) JAVA 7 (1) JAVA SE 、JAVA EE、JAVA ME (1) JAVA 日期 (1) JAVA-OCJP (1) JAVA-WEB (1) JAVA_IDE (1) JAVA其它 (1) JBoss Server (1) JDK (1) JMX (1) JRE (1) Java RMI (1) Java String (1) Joda Time (1) Linux_其它 (1) MySQL教學 (1) Oracle_VirtualBox (1) SQL Server (1) SWT (1) Session (1) Stack (1) Struts 2 (1) Tool (1) ZK Studio (1) csv (1) grails-其它類 (1) jQuery-進階 (1) java mail (1) java web (1) java8 (1) jsoup (1) mockmvc (1) modules (1) tomcat (1) win10 (1) 其它類 (1) 圖片工具 (1) 模擬器 (1) 讀書分享 (1) 開發資訊 (1)

精選文章

初學 Java 的 HelloWorld 程式

撰寫一個JAVA程式 public class HelloWorld{ public static void main(String[ ] args){ System.out.println("我第一支Java程式!!"); } } ...