传递与引用
2012-10-03 02:15
10 查看
Java中所有函数调用本质上都是值传递。首先我们来看这样一段程序:
输出结果为:
10
World
cello
这里涉及到的就是Java传递和引用的问题。Java中所有的函数本质上都是值传递,也就是说函数的形参是实参的一份副本。如果实参是基本类型,那么形参就是基本类型的值的副本;如果实参是引用类型,那么形参就是引用类型的句柄的副本。我们可以把值当做一个仓库,把引用类型句柄当做一把钥匙。这样我们再来看上面的几行代码。
变量 i 是基本类型,在执行函数 change(int i, String str, char []ch) 时,只是把 i 的值(10)的副本传给了形参中的 i ,可以想象成是在原来的仓库旁边有建了个仓库,往新仓库里放了20袋大米,但是新仓库里的东西和原来放10袋大米的仓库没有关系,所以最终打印的还是原来仓库中的10袋大米。
接下来先说一下char数组,在执行change 函数的时候,同样是将char数组的句柄传递给形参。上边我们说可以把句柄想象成钥匙,那在这里我们就试试。执行change的时候,我们把钥匙的副本(注意无论是值还是句柄,传递的都是副本)传给了ch,它用这把复制的钥匙一样可以打开原来存放 hello 的仓库,所以它打开了仓库,把 'h' 换成了 'c' ,最终打印的时候我们就看到了 cello 的结果。
至于String有些同学大概会有疑问,不是说除了四类八种之外都是引用类型么,那么String也是引用类型,那为什么str 的值没有改变呢?
确实,String属于引用类型,但是让我们来看看String类的一部分定义:
从Java中String的定义我们可以看出,String类及其成员变量都是final类型,即不能被更改的,这就相当于你拿了配好的钥匙副本但是却搬不动仓库里的东西,什么都动不了,所以在最后打印的时候str 的结果还是 World 不会变。
public class Test { public static void main(String[] args) { int i = 10; String str = new String("World"); char[] ch = { 'H', 'e', 'l', 'l', 'o' }; change(i, str, ch); System.out.println(i); System.out.println(str); ; System.out.println(ch); } public static void change(int i, String str, char[] ch) { i = 20; str = "Changed"; ch[0] = 'c'; } }
输出结果为:
10
World
cello
这里涉及到的就是Java传递和引用的问题。Java中所有的函数本质上都是值传递,也就是说函数的形参是实参的一份副本。如果实参是基本类型,那么形参就是基本类型的值的副本;如果实参是引用类型,那么形参就是引用类型的句柄的副本。我们可以把值当做一个仓库,把引用类型句柄当做一把钥匙。这样我们再来看上面的几行代码。
变量 i 是基本类型,在执行函数 change(int i, String str, char []ch) 时,只是把 i 的值(10)的副本传给了形参中的 i ,可以想象成是在原来的仓库旁边有建了个仓库,往新仓库里放了20袋大米,但是新仓库里的东西和原来放10袋大米的仓库没有关系,所以最终打印的还是原来仓库中的10袋大米。
接下来先说一下char数组,在执行change 函数的时候,同样是将char数组的句柄传递给形参。上边我们说可以把句柄想象成钥匙,那在这里我们就试试。执行change的时候,我们把钥匙的副本(注意无论是值还是句柄,传递的都是副本)传给了ch,它用这把复制的钥匙一样可以打开原来存放 hello 的仓库,所以它打开了仓库,把 'h' 换成了 'c' ,最终打印的时候我们就看到了 cello 的结果。
至于String有些同学大概会有疑问,不是说除了四类八种之外都是引用类型么,那么String也是引用类型,那为什么str 的值没有改变呢?
确实,String属于引用类型,但是让我们来看看String类的一部分定义:
public final class String implements java.io.Serializable, Comparable<String>, CharSequence { /** The value is used for character storage. */ private final char value[]; /** The offset is the first index of the storage that is used. */ private final int offset; /** The count is the number of characters in the String. */ private final int count; /** Cache the hash code for the string */ private int hash; // Default to 0 /** use serialVersionUID from JDK 1.0.2 for interoperability */ private static final long serialVersionUID = -6849794470754667710L;
从Java中String的定义我们可以看出,String类及其成员变量都是final类型,即不能被更改的,这就相当于你拿了配好的钥匙副本但是却搬不动仓库里的东西,什么都动不了,所以在最后打印的时候str 的结果还是 World 不会变。
相关文章推荐
- java值传递和引用传递
- java 值传递和引用传递
- Javaの值传递和引用传递
- 正确传递hash引用
- java中的值传递和引用传递
- C专家编程--指针和数组(三) 值传递 指针传递 引用传递
- C#中的参数传递:值类型(value type)和引用类型(reference type)
- C++ 值传递、指针传递、引用传递详解
- 关于java值传递跟引用传递的常见误区
- 浅谈Asp.net 多层架构中的变量引用与传递
- JavaScript强化教程——对象的值传递和引用传递
- 引用类型传递参数到底传的是值还是引用
- Java是值传递还是引用传递?
- 一个成功传递引用类型参数到非托管环境的例子
- java的值传递与引用传递
- PHP对象默认按引用传递
- 关于值传递和引用传递
- C++中值传递、指针传递、引用传递的总结
- 引用,指针,值传递的使用
- c++中使用引用传递来提高效率