public class myFz {
public static void fz(Integer a,Integer b)
{
a=9;
b=8;
}
public static void main(String[] args) {
// TODO Auto-generated method stub
Integer a=new Integer(10),b=new Integer(90);
mySwap.fz(a,b);
System.out.println(a);
System.out.println(b);
}
}
想请问为什么不能实现重新赋值啊
参数是什么传递方式呢?
能不能给我个存储模型示意图?
谢谢
10 个解决方案
#1
1) 局部变量
定义在方法内部,其作用域为所在代码块,也称为临时变量、栈变量。
存在于栈中。
2) 实例变量
定义在类内部方法之外,其作用域为整个类。如未定义初值,系统会自动为其赋黙认值。存在于堆中
默认数值
类型 黙认值
byte 0
short 0
int 0
long 0L
float 0.0f
double 0.0d
char '\u0000' 空格
boolean false
*All reference types null
你输出的是 a对象
而 a=9;是一个引用
package com.csdn;
import java.util.ArrayList;
public class TestFanxin {
public static void fz(Integer a,Integer b)
{
a=9;
b=8;
}
public static void main(String[] args) {
// TODO Auto-generated method stub
Integer a=new Integer(10),b=new Integer(90);
fz(a,b);
System.out.println(b);
//输出对象
TestFanxin test = new TestFanxin();
User u =test.new User("super对象");
System.out.println(u);
System.out.println(u.name);
}
class User {
String name = "123引用";
User(String name){
this.name = "super";
}
}
}
#2
看http://topic.csdn.net/u/20090523/21/c6c9028b-04de-4aef-8b9e-f63e8eb29864.html
这个帖子,5楼的回复,画图了,很方便理解。
这个帖子,5楼的回复,画图了,很方便理解。
#3
但是赋值是改变了对象本身的内容吧
是指向的对象变啦而指向的对象的地址没变啊?
#4
你的是plain class---说白了就是一个普通的栈对象,方法弹栈的时候就消失了。
a赋值。
b赋值
调用函数的时候 b弹栈,a弹栈.---方法调用完毕值消失。 对于一个普通的值对象你认为它还有放进堆中的必要么?
像大家说的那个什么对象就是引用,根本就是谬论,对象也要看是不是放在堆中。这话说完估计就一堆人PK我!!!!
程序在编译的时候方法分配了一段内存,而且分配了入口地址。java 不但有一个独特的值地址,而且名称在局部也可以引用地址。
如果你这么写:
public class User{
User(int a){
this.a=a;
}
int a=0;
}
swap(User a User b)
看看结果!!
为什么啊?
就是此时User进入了堆中,这个时候的a引用在栈中指向了堆。
a--->对象 (对象在栈中,方法调用就结束了,对象在堆中,方法调用完毕一样存在,JVM要是恶意回收那也没办法)
#5
顶!
#6
Integer也是基础类型来的,凡是八个基础类型都是值传递
其它的就是引用传递了
其它的就是引用传递了
#7
java是只有传值...
#8
应该是这八个基本数据类型所对应的封装类和String一样具有不可变性。
lz可以参考一下:
lz可以参考一下:
public class ParamTest {
public void changeInt(int a) {
a = 3;
}
public void changePoint(Point point) {
point.x = 5;
point.y = 6;
}
public void changeString(String str) {
str = "xyz";
}
public void change(char c, char[] ch) {
c = 'B';
ch[0] = 'Z';
}
public static void main(String[] args) {
// 第一个测试
int a = 1;
ParamTest test = new ParamTest();
test.changeInt(a);
System.out.println(a);
// 第二个测试------Java中的方法参数传递机制
// Point point = new Point(1, 2);
// ParamTest test = new ParamTest();
// test.changePoint(point);
// System.out.println(point.x);
// System.out.println(point.y);// 这说明是pass by value(对象传递它的引用)
// 第三个测试------String的不可变性
// String s = "abc";
// ParamTest test = new ParamTest();
// test.changeString(s);
// System.out.println(s);
// 第四个测试
// char c='A';
// char[] ch=new char[]{'M','N','P'};//数组也是对象(引用数据类型)
// ParamTest test=new ParamTest();
// test.change(c, ch);
// System.out.println(c);
// System.out.println(ch[0]);
}
}
class Point {
int x;
int y;
public Point(int x, int y) {
this.x = x;
this.y = y;
}
}
#9
之所以不能实现交换呢,你这个问题昨天已经在你的第一个帖子中有了最详细的解释,也是最彻底的解释(火龙果)。
我以前也不太明白,借楼主的帖子也让我明白了很多,在此也感谢一下楼主。
虽然是初学者,但也想发表一下自己的观点。大致就是一楼的那个观点,方法中参数的引用是有生命周期的。
上面这种情况不能实现交换。因为Integer a ,a这个引用的作用域就是fz这个方法中,出去这个方法它的作用就消失了。
b 也是一样的道理。所以SwapTest.fz(c,d);后没有达到想要的效果。
换一种方式,验证一下说的是否正确。将输出语句放在fz这个方法中。
实现了交换,这就验证了上面说的是正确的。引用是放在栈中的,创建的对象是放在堆中的
要想理解这些应该了解一些堆栈的知识。
我以前也不太明白,借楼主的帖子也让我明白了很多,在此也感谢一下楼主。
虽然是初学者,但也想发表一下自己的观点。大致就是一楼的那个观点,方法中参数的引用是有生命周期的。
public class SwapTest
{
public static void fz(Integer a,Integer b)
{
a = new Integer(9);
b = new Integer(99);
}
public static void main(String[] args)
{
Integer c=new Integer(10),d=new Integer(90);
SwapTest.fz(c,d);
System.out.println(c);
System.out.println(d);
}
}
上面这种情况不能实现交换。因为Integer a ,a这个引用的作用域就是fz这个方法中,出去这个方法它的作用就消失了。
b 也是一样的道理。所以SwapTest.fz(c,d);后没有达到想要的效果。
换一种方式,验证一下说的是否正确。将输出语句放在fz这个方法中。
public class SwapTest
{
public static void fz(Integer a,Integer b)
{
a = new Integer(9);
b = new Integer(99);
System.out.println(a);
System.out.println(b);
}
public static void main(String[] args)
{
Integer c=new Integer(10),d=new Integer(90);
SwapTest.fz(c,d);
//System.out.println(c);
//System.out.println(d);
}
}
实现了交换,这就验证了上面说的是正确的。引用是放在栈中的,创建的对象是放在堆中的
要想理解这些应该了解一些堆栈的知识。
#10
也要谢谢楼上的
都是初学者
以后还要互相学习
这个问题算是搞懂了
结贴喽!
#1
1) 局部变量
定义在方法内部,其作用域为所在代码块,也称为临时变量、栈变量。
存在于栈中。
2) 实例变量
定义在类内部方法之外,其作用域为整个类。如未定义初值,系统会自动为其赋黙认值。存在于堆中
默认数值
类型 黙认值
byte 0
short 0
int 0
long 0L
float 0.0f
double 0.0d
char '\u0000' 空格
boolean false
*All reference types null
你输出的是 a对象
而 a=9;是一个引用
package com.csdn;
import java.util.ArrayList;
public class TestFanxin {
public static void fz(Integer a,Integer b)
{
a=9;
b=8;
}
public static void main(String[] args) {
// TODO Auto-generated method stub
Integer a=new Integer(10),b=new Integer(90);
fz(a,b);
System.out.println(b);
//输出对象
TestFanxin test = new TestFanxin();
User u =test.new User("super对象");
System.out.println(u);
System.out.println(u.name);
}
class User {
String name = "123引用";
User(String name){
this.name = "super";
}
}
}
#2
看http://topic.csdn.net/u/20090523/21/c6c9028b-04de-4aef-8b9e-f63e8eb29864.html
这个帖子,5楼的回复,画图了,很方便理解。
这个帖子,5楼的回复,画图了,很方便理解。
#3
但是赋值是改变了对象本身的内容吧
是指向的对象变啦而指向的对象的地址没变啊?
#4
你的是plain class---说白了就是一个普通的栈对象,方法弹栈的时候就消失了。
a赋值。
b赋值
调用函数的时候 b弹栈,a弹栈.---方法调用完毕值消失。 对于一个普通的值对象你认为它还有放进堆中的必要么?
像大家说的那个什么对象就是引用,根本就是谬论,对象也要看是不是放在堆中。这话说完估计就一堆人PK我!!!!
程序在编译的时候方法分配了一段内存,而且分配了入口地址。java 不但有一个独特的值地址,而且名称在局部也可以引用地址。
如果你这么写:
public class User{
User(int a){
this.a=a;
}
int a=0;
}
swap(User a User b)
看看结果!!
为什么啊?
就是此时User进入了堆中,这个时候的a引用在栈中指向了堆。
a--->对象 (对象在栈中,方法调用就结束了,对象在堆中,方法调用完毕一样存在,JVM要是恶意回收那也没办法)
#5
顶!
#6
Integer也是基础类型来的,凡是八个基础类型都是值传递
其它的就是引用传递了
其它的就是引用传递了
#7
java是只有传值...
#8
应该是这八个基本数据类型所对应的封装类和String一样具有不可变性。
lz可以参考一下:
lz可以参考一下:
public class ParamTest {
public void changeInt(int a) {
a = 3;
}
public void changePoint(Point point) {
point.x = 5;
point.y = 6;
}
public void changeString(String str) {
str = "xyz";
}
public void change(char c, char[] ch) {
c = 'B';
ch[0] = 'Z';
}
public static void main(String[] args) {
// 第一个测试
int a = 1;
ParamTest test = new ParamTest();
test.changeInt(a);
System.out.println(a);
// 第二个测试------Java中的方法参数传递机制
// Point point = new Point(1, 2);
// ParamTest test = new ParamTest();
// test.changePoint(point);
// System.out.println(point.x);
// System.out.println(point.y);// 这说明是pass by value(对象传递它的引用)
// 第三个测试------String的不可变性
// String s = "abc";
// ParamTest test = new ParamTest();
// test.changeString(s);
// System.out.println(s);
// 第四个测试
// char c='A';
// char[] ch=new char[]{'M','N','P'};//数组也是对象(引用数据类型)
// ParamTest test=new ParamTest();
// test.change(c, ch);
// System.out.println(c);
// System.out.println(ch[0]);
}
}
class Point {
int x;
int y;
public Point(int x, int y) {
this.x = x;
this.y = y;
}
}
#9
之所以不能实现交换呢,你这个问题昨天已经在你的第一个帖子中有了最详细的解释,也是最彻底的解释(火龙果)。
我以前也不太明白,借楼主的帖子也让我明白了很多,在此也感谢一下楼主。
虽然是初学者,但也想发表一下自己的观点。大致就是一楼的那个观点,方法中参数的引用是有生命周期的。
上面这种情况不能实现交换。因为Integer a ,a这个引用的作用域就是fz这个方法中,出去这个方法它的作用就消失了。
b 也是一样的道理。所以SwapTest.fz(c,d);后没有达到想要的效果。
换一种方式,验证一下说的是否正确。将输出语句放在fz这个方法中。
实现了交换,这就验证了上面说的是正确的。引用是放在栈中的,创建的对象是放在堆中的
要想理解这些应该了解一些堆栈的知识。
我以前也不太明白,借楼主的帖子也让我明白了很多,在此也感谢一下楼主。
虽然是初学者,但也想发表一下自己的观点。大致就是一楼的那个观点,方法中参数的引用是有生命周期的。
public class SwapTest
{
public static void fz(Integer a,Integer b)
{
a = new Integer(9);
b = new Integer(99);
}
public static void main(String[] args)
{
Integer c=new Integer(10),d=new Integer(90);
SwapTest.fz(c,d);
System.out.println(c);
System.out.println(d);
}
}
上面这种情况不能实现交换。因为Integer a ,a这个引用的作用域就是fz这个方法中,出去这个方法它的作用就消失了。
b 也是一样的道理。所以SwapTest.fz(c,d);后没有达到想要的效果。
换一种方式,验证一下说的是否正确。将输出语句放在fz这个方法中。
public class SwapTest
{
public static void fz(Integer a,Integer b)
{
a = new Integer(9);
b = new Integer(99);
System.out.println(a);
System.out.println(b);
}
public static void main(String[] args)
{
Integer c=new Integer(10),d=new Integer(90);
SwapTest.fz(c,d);
//System.out.println(c);
//System.out.println(d);
}
}
实现了交换,这就验证了上面说的是正确的。引用是放在栈中的,创建的对象是放在堆中的
要想理解这些应该了解一些堆栈的知识。
#10
也要谢谢楼上的
都是初学者
以后还要互相学习
这个问题算是搞懂了
结贴喽!