2009-01-28 155 views
11

我有一个关于更改Java中方法中变量值的问题。在方法中更改变量的值,Java

这是我的代码:

public class Test { 
    public static void funk(int a, int[] b) { 
     b[0] = b[0] * 2; 
     a = b[0] + 5; 
    } 

    public static void main(String[] args) { 
     int bird = 10; 
     int[] tiger = {7}; 

     Test.funk(bird, tiger); 
    } 
} 

方法Test.funk(bird, tiger)执行后,鸟的价值没有改变 - 它仍然具有价值10,即使在funk()方法我们已经改变了值与a = b[0] + 5;

在另一方面,在阵列的变化元素的值,因为我们有说法b[0] = b[0] * 2;

我不明白为什么一件事情会改变,另一件事情不会改变?有人可以为我解释这一点。

回答

17

看看Jon Skeet的文章Parameter-Passing in Java,这解释了这一点。

在短(看他的网站更全的解释):

数组是引用类型。如果传递指向数组的引用,则会复制该引用的值并将其分配给该函数的参数。所以参数将指向与传递的参数相同的数组。因此,通过函数的参数对数组所做的更改将在调用函数中可见。但是,通过将参数(b)更改为null,参数(b)不会被调用函数注意到,因为参数(b)只是传递的参数(tiger)的副本。

整数是所谓的原始类型。传递整数复制其值并将其分配给参数。但是这个价值并不是对实际数据的参考,而是数据本身。因此,对函数中参数的更改将影响参数(a),但不会影响调用函数(bird)中传递的参数。

4

这是因为当你声明

public static void funk(int a, int[] b) 

变量的范围仅仅是方法。那么当你改变这个值的时候,你只是在改变变量的值的方法。

关于b。那是一个新的对象引用在主创建的同一个阵列,这就是为什么它似乎值不变化(变化的是下面的数组对象)

但试试这个:

public static void funk(int a, int[] b) { 
    // create a new reference for b 
    int[] c = new int[b.length]; 
    c[0] = b[0]; 
    b = c; 

    // The same. 
    b[0] = b[0] * 2; 
    a = b[0] + 5; 
} 

当你这样做你会发现老虎的价值也没有变化(只有在funk中创建的新数组c的内容)

您可以使用包装器模拟通过ref传递。See this post.

虽然我还没有得到有关只是为了乐趣

编辑任何意见:

我修改代码以使用上面贴包装。

它看起来很奇怪,但看起来像它的作品。

// By ref simulated. 
public class Test { 

    public static void funk(_<Integer> a, int[] b) { 
     b[0] = b[0] * 2; 
     a.s( b[0] + 5) ; 
    } 

    public static void main(String[] args) { 
     _<Integer> bird = new _<Integer>(10); 
     int[] tiger = {7}; 

     Test.funk(bird , tiger); 

     System.out.println("bird = " + bird); 
     System.out.println("tiger = " + tiger[0]); 

    } 

} 

打印

bird = 19 
tiger = 14 

:-S

4

基本上,对象(如阵列)被传递到方法 “通过引用”。所以当你改变对象时,它会改变传入方法的同一个对象。

基元(如int)的“按值传递”,让您在一个赋值给变量是不一样的传递英寸

我希望这有助于int变量.. 。

+1

不,它并不能帮助。 Java总是传递值。阅读其他答案中提供的链接;你需要明白这一点。 – 2009-01-29 03:29:43