Java 引用传递与值传递

Java 引用传递与值传递

【背景】

首先 Java 中没有值传递和引用传递的概念,所谓 pass by value 和 pass by reference 只是从其他语言引申的概念而已。所以你会听到有人说 ”Java 中没有引用传递,全部都是值传递“,然而在使用过程中却又总能遇到 ”方法调用确实改变了某些值“ 的情况。

一、基本类型与引用类型

基本类型:byte/char/int/long/float/double

引用类型:除了上述类型之外的类型,包括各种扩展类型(Integer/Character/Double等),String,实体类,List 等;

int num = 10;
String str = "hello";
num - 10
str - 0x11
hello

​ 如图所示,num是基本类型,值就直接保存在变量中。而str是引用类型,变量中保存的只是实际对象的地址。一般称这种变量为"引用",引用指向实际对象,实际对象中保存着内容。

二、赋值运算符 ”=“

​ 当使用赋值运算符时,会发生什么?

num = 20;
str = "word";
num - 20
0x11
hello
str - 0x12
word

​ 对于基本类型,赋值直接改变了值。对于引用类型而言,new了一个新对象 word,并将str中保存的地址更新为了新的地址。由于原地址0x11不再持有任何引用,(0x11 -> hello) 会被垃圾回收掉。

三、方法调用时发生了什么
// 第一个例子:基本类型
void foo(int value) {
    value = 100;
}
// num 没有被改变
foo(num);

// 第二个例子:没有提供改变自身方法的引用类型
void foo(String text) {
    text = "windows";
}
// str 也没有被改变
foo(str);

// 第三个例子:提供了改变自身方法的引用类型
StringBuilder sb = new StringBuilder("iphone");
void foo(StringBuilder builder) {
    builder.append("11pro");
}
// sb 被改变了,变成了"iphone11pro"
foo(sb); 

// 第四个例子:提供了改变自身方法的引用类型,但是不使用,而是使用赋值运算符。
StringBuilder sb = new StringBuilder("iphone");
void foo(StringBuilder builder) {
    builder = new StringBuilder("ipad");
}
// sb 没有被改变,还是 "iphone"。
foo(sb); 

// 第五个例子:List
List<User> userList = new ArrayList<>();
void foo(List<User> list) {
    // 有效
    userList.add(new User("aaaaa", 2));
    userList = new ArrayList<>();
    // 无效
    userList.add(new User("bbbbb",1));
}


/*
	【总结】
	1. 使用 = 对方法参数赋值的,都不能改变调用者的值
	2. 使用引用类型提供的改变自身的方法 (如 List.add(); StringBuilder.append(); )
			可以改变其值 (类似引用传递)
*/
四、都是这样的吗
int[][] arr3 = new int[3][3];
setArr(arr3);
private static void setArr(int[][] arr3) {
    // 有效
    arr3[2][1] = 1;
    // 有效
    arr3[1] = new int[] {1,2,3};
    // 无效
    arr3 = new int[5][6];
}

不能完全按照 ”=“ 操作来判断是否为 ”引用传递“ 。 因为在以上代码中,实例化的二维数组中,arr3 处保存了一个地址(栈区),指向了其实际值的位置(堆区)。

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值