首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 相關知識

Java 方法參數傳遞機制深度解析:值傳遞與引用傳遞的本質區別

     編輯:Java 相關知識

結論先行

Java 只有值傳遞。基本類型傳值副本,引用類型傳引用副本(地址值),但引用指向同一對象。

驗證實驗

static class Value { String val = "old"; }
public static void newValue(Value v) {
    v = new Value();           // 修改局部引用指向
    v.val = "new";
    System.out.println("方法內: " + v.val + " hash=" + v.hashCode());
}
public static void modifyValue(Value v) {
    v.val = "new";             // 修改對象內部狀態
    System.out.println("方法內: " + v.val + " hash=" + v.hashCode());
}
public static void main(String[] args) {
    Value v1 = new Value();
    System.out.println("調用前: " + v1.val + " hash=" + v1.hashCode());
    newValue(v1);
    System.out.println("調用後: " + v1.val + " hash=" + v1.hashCode()); // 未變
    Value v2 = new Value();
    System.out.println("調用前: " + v2.val + " hash=" + v2.hashCode());
    modifyValue(v2);
    System.out.println("調用後: " + v2.val + " hash=" + v2.hashCode()); // 已變
}

輸出結果分析

調用前: old hash=12677476
方法內: new hash=33263331
調用後: old hash=12677476   ← newValue 未影響外部
調用前: old hash=6413875
方法內: new hash=6413875
調用後: new hash=6413875    ← modifyValue 修改了同一對象

內存模型圖解

  • 棧:存放局部變量(基本類型值、引用地址)
  • 堆:存放對象實例
  • 調用方法時,引用地址被按值複製到參數槽,兩個引用指向同一堆對象
  • 參數重新賦值(v = new Value())只改變棧中副本,不影響實參引用
  • 通過參數調用 setXxx() 修改堆對象內容,外部可見

偽代碼還原

// newValue
ref_copy = ref_original;        // 複製引用地址
ref_copy = new Value();         // 指向新對象
ref_copy.setVal("new");         // 操作新對象

// modifyValue
ref_copy = ref_original;        // 複製引用地址
ref_copy.setVal("new");         // 操作原對象

實戰建議

  1. 方法參數不要重新賦值,專注於修改對象狀態
  2. 需要返回新對象時,用返回值而非參數輸出
  3. 不可變對象(String、Integer、BigDecimal)天然安全,無副作用
  4. 大對象傳遞考慮防禦性拷貝避免意外修改
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved