java中参数传递--值传递,引用传递
java中的参数传递——值传递、引用传递
参数是按值而不是按引用传递的说明 Java 应用程序有且仅有的一种参数传递机制,即按值传递。
在 Java 应用程序中永远不会传递对象,而只传递对象引用。因此是按引用传递对象。Java 应用程序按引用传递对象这一事实并不意味着 Java 应用程序按引用传递参数。参数可以是对象引用,而 Java 应用程序是按值传递对象引用的。
Java 应用程序中的变量可以为以下两种类型之一:引用类型或基本类型。当作为参数传递给一个方法时,处理这两种类型的方式是相同的。两种类型都是按值传递的;没有一种按引用传递。
按值传递和按引用传递。按值传递意味着当将一个参数传递给一个函数时,函数接收的是原始值的一个副本。因此,如果函数修改了该参数,仅改变副本,而原始值保持不变。按引用传递意味着当将一个参数传递给一个函数时,函数接收的是原始值的内存地址,而不是值的副本。因此,如果函数修改了该参数,调用代码中的原始值也随之改变。
1、对象是按引用传递的
2、Java 应用程序有且仅有的一种参数传递机制,即按值传递
3、按值传递意味着当将一个参数传递给一个函数时,函数接收的是原始值的一个副本
4、按引用传递意味着当将一个参数传递给一个函数时,函数接收的是原始值的内存地址,而不是值的副本
首先考试大来看看第一点:对象是按引用传递的
确实,这一点我想大家没有任何疑问,例如:
class Test01
{
public static void main(String[] args)
{
StringBuffer s= new StringBuffer("good");
StringBuffer s2=s;
s2.append(" afternoon.");
System.out.println(s);
}
}
对象s和s2指向的是内存中的同一个地址因此指向的也是同一个对象。
如何解释“对象是按引用传递的”的呢?
这里的意思是进行对象赋值操作是传递的是对象的引用,因此对象是按引用传递的,有问题吗?
程序运行的输出是:
good afternoon.
这说明s2和s是同一个对象。
这里有一点要澄清的是,这里的传对象其实也是传值,因为对象就是一个指针,这个赋值是指针之间的赋值,因此在java中就将它说成了传引用。(引用是什么?不就是地址吗?地址是什么,不过就是一个整数值)
再看看下面的例子:
class Test02
{
public static void main(String[] args)
{
int i=5;
int i2=i;
i2=6;
System.out.println(i);
}
}
程序的结果是什么?5!!!
这说明什么,原始数据类型是按值传递的,这个按值传递也是指的是进行赋值时的行为下一个问题:Java 应用程序有且仅有的一种参数传递机制,即按值传递
class Test03
{
public static void main(String[] args)
{
StringBuffer s= new StringBuffer("good");
StringBuffer s2=new StringBuffer("bad");
test(s,s2);
System.out.println(s);//9
System.out.println(s2);//10
}
static void test(StringBuffer s,StringBuffer s2) {
System.out.println(s);//1
System.out.println(s2);//2
s2=s;//3
s=new StringBuffer("new");//4
System.out.println(s);//5
System.out.println(s2);//6
s.append("hah");//7
s2.append("hah");//8
}
}
程序的输出是:
good
bad
new
good
goodhah
bad
考试大提示: 为什么输出是这样的?
这里需要强调的是“参数传递机制”,它是与赋值语句时的传递机制的不同。
我们看到1,2处的输出与我们的预计是完全匹配的
3将s2指向s,4将s指向一个新的对象
因此5的输出打印的是新创建的对象的内容,而6打印的原来的s的内容
7和8两个地方修改对象内容,但是9和10的输出为什么是那样的呢?
Java 应用程序有且仅有的一种参数传递机制,即按值传递。
至此,我想总结一下我对这个问题的最后的看法和我认为可以帮助大家理解的一种方法:
我们可以将java中的对象理解为c/c++中的指针
例如在c/c++中:
int *p;
print(p);//1
*p=5;
print(*p);//2
1打印的结果是什么,一个16进制的地址,2打印的结果是什么?5,也就是指针指向的内容。
即使在c/c++中,这个指针其实也是一个32位的整数,我们可以理解我一个long型的值。
而在java中一个对象s是什么,同样也是一个指针,也是一个int型的整数(对于JVM而言),我们在直接使用(即s2=s这样的情况,但是对于System.out.print(s)这种情况例外,因为它实际上被晃猄ystem.out.print(s.toString()))对象时它是一个int的整数,这个可以同时解释赋值的传引用和传参数时的传值(在这两种情况下都是直接使用),而我们在s.XXX这样的情况下时s其实就是c/c++中的*s这样的使用了。这种在不同的使用情况下出现不同的结果是java为我们做的一种简化,但是对于c/c++程序员可能是一种误导。java中有很多中这种根据上下文进行自动识别和处理的情况,下面是一个有点极端的情况:
class t
{
public static String t="t";
public static void main(String[] args)
{
t t =new t();
t.t();
}
static void t() {
System.out.println(t);
}
}
1.对象就是传引用
2.原始类型就是传值
3.String类型因为没有提供自身修改的函数,每次操作都是新生成一个String对象,所以要特殊对待。可以认为是传值。
java中参数传递--值传递,引用传递的更多相关文章
- 在Java中字符串是通过引用传递的?
这是一个经典的java问题.在stackoverflow上,许多类似的问题已经被问过了,但是许多回答是错误的或不完整的. 如果你不想深入思考的话,这个问题很简单.如果你想明白的更彻底,那么问题可能容易 ...
- java中参数传递的问题
public class Test { public static void main(String[] args) { StringBuffer a = new StringBuffer(" ...
- Java 中的值传递和参数传递
Java中没有指针,所以也没有引用传递了,仅仅有值传递不过可以通过对象的方式来实现引用传递 类似java没有多继承 但可以用多次implements 接口实现多继承的功能 值传递:方法调用时,实际参数 ...
- 一道笔试题来理顺Java中的值传递和引用传递
题目如下: private static void change(StringBuffer str11, StringBuffer str12) { str12 = str11; str11 = ...
- Java中的值传递和地址传递(传值、传引用)
首先,不要纠结于 Pass By Value 和 Pass By Reference 的字面上的意义,否则很容易陷入所谓的“一切传引用其实本质上是传值”这种并不能解决问题无意义论战中.更何况,要想知道 ...
- java中的值传递和引用传递区别
值传递:(形式参数类型是基本数据类型):方法调用时,实际参数把它的值传递给对应的形式参数,形式参数只是用实际参数的值初始化自己的存储单元内容,是两个不同的存储单元,所以方法执行中形式参数值的改变不影响 ...
- 第002弹:Java 中的值传递和引用传递
在 Java 的代码开发过程中,为了尽可能提高方法的复用性,明确方法的作用,同时防止一个方法内部过于臃肿的问题,往往会创建许多方法,那么不可避免地会涉及到参数传递的问题.通常来说,我们将 Java 中 ...
- (转)Java中的值传递和引用传递
Java中的值传递和引用传递 当一个对象被当作参数传递到一个方法后,此方法可改变这个对象的属性,并可返回变化后的结果,那么这里到底是值传递还是引用传递? 答:是值传递.Java 编程语言只有值 ...
- 如何形象简单地理解java中只有值传递,而没有引用传递?
首先,java中只有值传递,没有引用传递.可以说是"传递的引用(地址)",而不能说是"按引用传递". 按值传递意味着当将一个参数传递给一个函数时,函数接收的是原 ...
随机推荐
- BZOJ4999 This Problem Is Too Simple!(树上差分+dfs序+树状数组)
对每个权值分别考虑.则只有单点加路径求和的操作.树上差分转化为求到根的路径和,子树加即可.再差分后bit即可.注意树上差分中根的父亲是0,已经忘了是第几次因为这个挂了. #include<ios ...
- BZOJ3613 HEOI2014南园满地堆轻絮
不明白在某谷上是怎么标到紫的.二分答案或者发现答案就是最大逆序差的一半. #include<iostream> #include<cstdio> #include<cma ...
- BZOJ1996 HNOI2010合唱队(区间dp)
设f[i][j][0/1]表示i~j这段区间上一次选择的是最左/最右人的方案数.转移显然. #include<iostream> #include<cstdio> #inclu ...
- 【比赛】HNOI2018 道路
这题很考思维啊,考验我们能否快速从省选难度跳转到普及难度 考试的时候真的想得太多,觉得省选不可能这么简单吧,然后就打脸 设 \(f[i][j][x]\) 表示从根到 \(x\) 号点,有 \(i\) ...
- Tajo--一个分布式数据仓库系统(设计架构)
上一篇Tajo--一个分布式数据仓库系统(概述)废话了一通,下面介绍一下Tajo的体系结构.以及官方的实验成果吧 一.体系架构 Tajo采用了Master-Worker架构(下图虚线框目前还在计划中) ...
- 【BZOJ3242】【NOI2013】快餐店(动态规划)
[BZOJ3242][NOI2013]快餐店(动态规划) 题面 BZOJ 题解 假设我们要做的是一棵树,那么答案显然是树的直径的一半. 证明? 假设树的直径是\(2d\),那么此时最远点的距离是\(d ...
- BZOJ5333 [Sdoi2018]荣誉称号 【差分 + 树形dp】
题目链接 BZOJ5333 题解 看到式子,立即想到二叉树上一个点及其\(k\)个父亲权值和[如果有的话]模\(m\)意义下为\(0\) 考虑如何满足条件 我们假设\(1\)号为第\(0\)层 那么我 ...
- Python精要参考(第二版)
ython 精要参考(第二版) 是Python语言初学者不错的参考学习用书,本系列译自Python Essential Reference, Second Edition 希望本系列可以给python ...
- max os取消开机启动
原文:http://liuzhichao.com/p/1667.html 安装MAMP后,启动服务时提示Apache启动失败,80端口被占用.查看进程发现存在几个httpd. OS X自带Apache ...
- 2-sat问题学习记录
如果你不知道什么是sat问题,请看以下问答. Q:sat问题是什麽?A:首先你有n个布尔变量,然后你有一个关于这n个布尔变量的布尔表达式,问你,如果让你随意给这n个布尔变量赋值,这个布尔表达式能否成立 ...