- 浏览: 198435 次
- 性别:
- 来自: 哈尔滨
文章分类
- 全部博客 (267)
- java.lang (8)
- 问题汇总 (21)
- 异常记录 (20)
- 功能实现 (19)
- 面试总结 (25)
- 技巧总结 (8)
- 常用代码 (4)
- 编程习惯 (3)
- 编码规则 (3)
- java.util (10)
- java.io (1)
- JavaWeb (9)
- MySQL (16)
- SVN (3)
- MyBatis (11)
- Velocity (7)
- 其他知识 (10)
- 人生哲理 (1)
- 人生故事 (1)
- 自我感悟 (1)
- shiro (3)
- 基础知识 (0)
- 问题总结 (1)
- Spring 标签 (1)
- Spring (3)
- 点滴生活 (1)
- DOS (1)
- CAS (4)
- Linux (9)
- Storm (6)
- Shell (1)
- regex (1)
- Collection (4)
- poi (1)
- 经典语句 (1)
- NIO (5)
- concurrent (14)
- RPC (1)
- zookeeper (3)
- 待整理 (2)
- Hadoop (9)
- RabbitMq (2)
- flume (1)
- hive (7)
- hbase (4)
- kafka (1)
- scala (1)
- GC (0)
- java.util.concurrent.atomic (1)
- java.lang.ref (6)
- JVM (2)
- algorithm (1)
- conception (1)
- java key word (1)
- sun.misc (1)
最新评论
一、值传递与引用传递
其实按值还是按引用的区别在于“是否在传递的时候进行对象的内存拷贝”,
java中基本类型是由于在JVM中存储区域不同于普通对象所以传递前会拷贝,传递的是拷贝后的值,
但是对象在传递的时候不拷贝,直接传“引用值”,指向同一片对象堆内存区域
二、基本数据类型
输出结果:
10
10
基本数据类型
main() 方法向 change() 中传递的是 栈中a 所存储的内容 10
change() 方法,形参 a ,虽然与 main() 中,名称相同,但是两个不同的变量
对应的包装类
其底层实现中value是final修饰,是不可改变的
与String 类似,其值是不可变更的
若欲通过change() 修改数值:
通过change()的返回值,重新赋值给 main()中的a
结论:
基本数据类型及对应的包装类在传递过程中,不会改变其所指向的内容
三、String 类型
字符串只要赋值就相当于新new一个对象,字符串变量指向这个新new的对象,之前的对象就成了没有引用指向的对象了。
1.String 的两种声明方式
String str = "abc"
栈中建立 str
判断堆中是否已有"abc",无则创建新的匿名空间,存放 "abc"
匿名空间首地址存放在 str 中,即 str 指向堆中的此空间
String str = new String("abc")
栈中建立 str
判断堆中是否已有"abc",无则创建新的匿名空间,存放 "abc"
堆中开辟新的空间,存放 "abc"
新的空间首地址存放在 str 中,匿名空间因无引用,过后被GC回收
备注:
提高程序运行效率,优选第一种方式
2.
String str = "abc" ;
未显示调用 new 操作,在编译时 相当于 new String("abc");
3.
change(String str);
此处的str 不同于 main() 中的 str ,相当于重新开辟了一个空间,虽然名称相同
调用方法时,main() 方法将 str = "abc" 的堆空间地址传递给了 change() 中的str
此时 main() change() 中的两个不同的 str 均指向同一个堆内存块
但 str = "bcd" ; 相当于 在堆中新开辟了一块空间,存放 "bcd",并将地址存放在了str 中
即 change() 中的 str 指向了新的堆中的地址 -- "bcd" 的地址,与 main() 中的 str 指向的 "abc" 无关了,在 change() 中对 str 的修改,也与 main() 中无关,所以值没有改变
四、引用类型
main() 中,建立引用对象,在堆中开辟新的空间
change() 中,形参声明新的对象,与main的不同
main() 调用 change() 时,将 栈中存放的堆中空间的首地址传递给 change() 中的参数
两者指向同一个数据地址
所以,change() 中的操作影响 main() 中的数据内容
输出:20
调用 change() ,与 main() 中 p 是两个不同的句柄,但此时指向同一个堆中的地址
setAge(20) 有效
重新new 一个p ,此时 change() 中的 p 与 main() 的 p 指向的堆中的地址已经不一样了
new 新开辟空间,一定与之前的不同
所以 setAge(30) 对 main() 中的无影响
其实按值还是按引用的区别在于“是否在传递的时候进行对象的内存拷贝”,
java中基本类型是由于在JVM中存储区域不同于普通对象所以传递前会拷贝,传递的是拷贝后的值,
但是对象在传递的时候不拷贝,直接传“引用值”,指向同一片对象堆内存区域
二、基本数据类型
public class IntegerTest { /** * @param args */ public static void main(String[] args) { int a = 10 ; Integer b = new Integer(10); IntegerTest test = new IntegerTest(); test.change(a); test.change(b); System.out.println(a); System.out.println(b); } public int change(Integer a){ a = a + 10 ; return a ; } }
输出结果:
10
10
基本数据类型
main() 方法向 change() 中传递的是 栈中a 所存储的内容 10
change() 方法,形参 a ,虽然与 main() 中,名称相同,但是两个不同的变量
对应的包装类
// Integer 的 value 是 final 修饰的 /** * The value of the <code>Integer</code>. * * @serial */ private final int value;
其底层实现中value是final修饰,是不可改变的
与String 类似,其值是不可变更的
若欲通过change() 修改数值:
通过change()的返回值,重新赋值给 main()中的a
结论:
基本数据类型及对应的包装类在传递过程中,不会改变其所指向的内容
三、String 类型
public class StringChangeTest { /** * @param args */ public static void main(String[] args) { String str = "abc" ; new StringChangeTest().change(str); System.out.println(str); } public void change(String str){ str = "bcd"; } }
字符串只要赋值就相当于新new一个对象,字符串变量指向这个新new的对象,之前的对象就成了没有引用指向的对象了。
1.String 的两种声明方式
String str = "abc"
栈中建立 str
判断堆中是否已有"abc",无则创建新的匿名空间,存放 "abc"
匿名空间首地址存放在 str 中,即 str 指向堆中的此空间
String str = new String("abc")
栈中建立 str
判断堆中是否已有"abc",无则创建新的匿名空间,存放 "abc"
堆中开辟新的空间,存放 "abc"
新的空间首地址存放在 str 中,匿名空间因无引用,过后被GC回收
备注:
提高程序运行效率,优选第一种方式
2.
String str = "abc" ;
未显示调用 new 操作,在编译时 相当于 new String("abc");
3.
change(String str);
此处的str 不同于 main() 中的 str ,相当于重新开辟了一个空间,虽然名称相同
调用方法时,main() 方法将 str = "abc" 的堆空间地址传递给了 change() 中的str
此时 main() change() 中的两个不同的 str 均指向同一个堆内存块
但 str = "bcd" ; 相当于 在堆中新开辟了一块空间,存放 "bcd",并将地址存放在了str 中
即 change() 中的 str 指向了新的堆中的地址 -- "bcd" 的地址,与 main() 中的 str 指向的 "abc" 无关了,在 change() 中对 str 的修改,也与 main() 中无关,所以值没有改变
四、引用类型
public class ArrayIntegerTest { /** * @param args */ public static void main(String[] args) { int [] a1 = {1,2,3,4,5}; new ArrayIntegerTest().change(a1); for(int i = 0 ; i < a1.length ; i++){ System.out.println(a1[i]); } int [] a12 = new int[]{1,2,3,4,5}; new ArrayIntegerTest().change(a12); for(int i = 0 ; i < a12.length ; i++){ System.out.println(a12[i]); } Integer [] a2 = {1,2,3,4,5}; new ArrayIntegerTest().change(a2); for(int i = 0 ; i < a2.length ; i++){ System.out.println(a2[i]); } char [] s1 = {'1','2','3'}; new ArrayIntegerTest().change(s1); System.out.println(new String(s1)); } public void change(int[] a){ a[0] = 10 ; } public void change(Integer[] a){ a[0] = 10 ; } public void change(char[] a){ a[0] = 'a'; } }
main() 中,建立引用对象,在堆中开辟新的空间
change() 中,形参声明新的对象,与main的不同
main() 调用 change() 时,将 栈中存放的堆中空间的首地址传递给 change() 中的参数
两者指向同一个数据地址
所以,change() 中的操作影响 main() 中的数据内容
public class PersonTest { /** * @param args */ public static void main(String[] args) { Person p = new Person(); p.setAge(10); new PersonTest().change(p); System.out.println(p.getAge()); } public void change(Person p){ p.setAge(20); p = new Person(); p.setAge(30); } } class Person{ private int age ; public int getAge() { return age; } public void setAge(int age) { this.age = age; } }
输出:20
调用 change() ,与 main() 中 p 是两个不同的句柄,但此时指向同一个堆中的地址
setAge(20) 有效
重新new 一个p ,此时 change() 中的 p 与 main() 的 p 指向的堆中的地址已经不一样了
new 新开辟空间,一定与之前的不同
所以 setAge(30) 对 main() 中的无影响
发表评论
-
京东商城--商城研发部面试
2017-12-01 19:30 5482017年12月01日 笔试题目 1. final fina ... -
海量日志数据,提取出某日访问百度次数最多的那个IP
2017-11-29 21:18 2179问题:一个的日志文件中存放IP地址,按照访问量对IP地址取访问 ... -
输出十进制数字的二进制数的表示
2017-11-03 23:16 1051一、代码如下: public static void m ... -
将数组中的内容随机打乱
2017-10-27 22:45 467问题:斗地主游戏,开局会将纸牌重新打乱,请用数组的随机排序实现 ... -
JVM基础
2017-10-26 22:41 375一、Java 运行时区域 《 ... -
String为什么使用final 修饰
2017-10-25 22:32 911主要是为了”安全性“和”效率“的缘故 1、由于String类 ... -
沐金地面试记录
2017-10-25 22:15 45710.25 下午同事帮忙投递的,约在晚上面试,下班之后赶紧去了 ... -
JD广告部面试经历
2017-10-23 16:46 385同事的同事招聘,于是同事帮忙推荐了一下! 2017年10月1 ... -
编程题目(一)
2017-09-28 22:28 3631.函数:参数为两个字符串a,b ,判断 b 中是否包含 a ... -
装箱与拆箱
2016-10-24 22:46 467public class IntegerTest { ... -
可变性与不可变性
2015-06-01 20:55 405String StringBuilder StringBuff ... -
CS架构和BS架构的区别
2015-05-25 08:50 435一、简介 1.C/S结构,即 ... -
HTTP常见响应状态码
2015-05-20 08:26 380问题:程序调试过程中 ... -
JIT的概念
2015-05-19 18:48 657参考文献: http://blog.csdn.net/yan ... -
JDK与JRE与JVM的区别
2015-05-19 18:45 10501.JDK (1)概念 JDK : Java Developm ... -
运行时与编译时
2015-05-17 18:05 496运行时与编译时 博文转载:http://www.import ... -
System.exit(0)与return的区别
2015-05-17 16:49 967问题:System.exit(0)与return的区别 1. ... -
重载(overloading)与重写(overriding)
2015-05-17 15:50 594问题:重载(overloading)与重写(overridin ... -
==和equals
2015-05-15 20:07 612参考文献: http://www.cnblogs.com/zh ... -
return finally 与 System.exit(n)
2015-05-10 18:00 600问题:System.exit(n);的含义以及作用 说明: ...
相关推荐
一个实例让你明白什么是值传递和引用传递的!
数组总结(概念、定义、默认值、可变长参数、值传递与引用传递等)。1.冒泡排序: 两两相比(两个相邻的数进行比较) 条件成立 互换位置 外层循环控制比较的轮数 **轮数永远是 长度 -1 (n - 1)** 内层循环...
不管是按值传递还是按引用传递,都是把栈中的数据备份了一份给参数变量,只不过值类型备份的是具体的数值,而引用类型备份的是内存地址
第04章 面向对象(上) 08 值传递与引用传递
NULL 博文链接:https://chaozhichen.iteye.com/blog/762633
这是我总结的一些知识点应该可以供老师们进行讲解
Java:按值传递还是按引用传递详细解说
《值传递和引用传递.pdf》介绍了值传递和引用传递的用法和区别
首先讨论函数之前,先弄清楚基本类型值与引用类型值的复制问题 一、数据类型的复制分析 内存分为栈区(stack)和堆区(heap) ,如果将内存看成一本书,栈好比是书的目录,而堆就是书的内容,基本类型可以看成内容...
java 值传递和引用传递的比较区别,包括代码及详解
Java面向对象值传递和引用传递Java面向对象值传递和引用传递Java面向对象值传递和引用传递Java面向对象值传递和引用传递
另一方面,值传递由于形参和实参内存地址不一样,有些功能并不能实现(swap()),因此,除了极为简单的函数会使用值传递外,大多数会采用引用传递。而对于指针传递,则在涉及数组的情况下使用较多,因为指针本身会给...
主要介绍了JAVA参数传递方式,结合实例形式分析了java按值传递与引用传递区别及相关操作注意事项,需要的朋友可以参考下
C#笔记(基础)值传递和引用传递,适合刚开始学习C#的朋友来学习,阅览
主要介绍了Go 值传递与引用传递的方法,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
#值传递和引用传递 python中数据类型有:整形,字条串,元组,列表,字典,集合 不可变数据类型:当该数据类型对应变量的值变化,值对应的内存地址 也发生变化,这个值就为不可变数据类型 可变数据类型:当该数据...
主要介绍了java到底是值传递还是引用传递的相关知识,本文通过几个例子给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
java学习java语言的值传递和引用传递
本人经过长时间收集的最经典、最有说服力、最易懂的关于值传递和引用传递的详解资料~包看包会~发出去真有些不舍得~
Js引用类型按值传递的题目:两个变量间赋值时,以及作为变量给函数传参时,只是将原变量中的值复制一个副本给对方变量或形参变量 i. 对于原始类型的值,修改新变量,不影响原变量 ii. 对于引用类型的值的值,因为...