在java中将对象传递给方法似乎是通过引用(而Java是通过val)

我认为当你将对象传递给Java中的方法时,它们应该是有价值的。

这是我的代码:

public class MyClass{
    int mRows;
    int mCols;
    Tile mTiles[][];     //Custom class

    //Constructor
    public MyClass(Tile[][] tiles, int rows, int cols) {
        mRows = rows;
        mCols = cols;

        mTiles = new Tile[mRows][mCols];
        for (int i=0; i < mRows; i++) {
            for (int j=0; j < mCols; j++) {
                mTiles[i][j] = new Tile();
                mTiles[i][j] = tiles[i][j];
            }
        }
    }

此时,对mTiles对象的任何更改mTiles反射回tile对象。 任何想法如何解决这一问题?

谢谢大家。


这是通过val,但是当谈论对象时,传递的是参考的值,因此,如果您的对象是可变的(如您的示例中)通过参考副本修改对象,将修改下层对象。

要解决它,你必须复制你的对象并传递新的参考值。

在你的代码中,你在“瓷砖”和“mTiles”中使用相同的参考值

mTiles[i][j] = new Tile(); // <---this line is useless by the way
mTiles[i][j] = tiles[i][j] // because you then assign the same value here

你将不得不像这样创建一个新的:

mTiles[i][j] = new Tile(tiles[i][j]);

要么

mTiles[i][j] = tiles[i][j].clone();

要么

mTiles[i][j] = Tile.newFrom( tiles[i][j] );

或者类似的东西,所以你可以创建一个新的,而不是使用相同的参考。

我希望这有帮助。

编辑

当您在pass-by-val中更改参考时,原始参数不受影响,即:

String s = "hi"; 
changeIt(s);
....
void changeIt(String s){ 
    s = "bye" // assigning to the copy a new ref value of "bye"
}

在此之后,原来的“嗨”仍然是“嗨”。 在传递中它将是“再见”

这里有一些链接:

http://www.javaranch.com/campfire/StoryPassBy.jsp

有人可以向我解释在Java中传递“value”而不是“reference”是什么原因?

通过引用传递或通过值传递?

http://www.javaworld.com/javaworld/javaqa/2000-05/03-qa-0526-pass.html

http://academic.regis.edu/dbahr/GeneralPages/IntroToProgramming/JavaPassByValue.htm

http://www.jguru.com/faq/view.jsp?EID=430996

最终:

http://www.google.com.mx/search?sourceid=chrome&ie=UTF-8&q=java+is+pass+by+value


你不传递对象,你传递一个对象的引用,这是通过值复制的。


以下是Java参数传递语义的一些诊断示例:

对于一个对象类型:

void changeIt(String s) {
    s = "bye";
}

String s = "hi"; 
changeIt(s);
System.out.println(s);  // would print "bye" for call by reference
                        // but actually prints "hi"

对于原始类型:

void changeIt(int i) {
    i = 42;
}

int i = 0; 
changeIt(i);
System.out.println(i);  // would print "42" for call by reference
                        // but actually prints "0"

实际上,在这两个例子中, changeIt方法中的赋值只影响相应方法的局部变量,打印的实际值将是“hi”和“0”。

编辑

由于OP 仍然不相信我......这里有一个诊断示例,表明Java也是可变对象的按值调用。

public class Mutable {
    int field;
    public Mutable(int field) { this.field = field; }
    public void setField(int field) { this.field = field; }
    public int getField() { return field; }
}

void changeIt(Mutable m, Mutable m2) {
    m = m2;  // or 'm = new Mutable(42);' or 'm = null;'
}

Mutable m = new Mutable(0); 
Mutable m2 = new Mutable(42); 
changeIt(m, m2);
System.out.println(m.getField());  
                        // would print "42" for call by reference
                        // but actually prints "0"

相比之下,这个例子对于引用调用和值调用语义都会给出相同的答案 。 它没有证明任何关于参数传递语义。

void changeIt2(Mutable m) {
    m.setField(42);
}

Mutable m = new Mutable(); 
changeIt2(m);
System.out.println(m.getField());  
                        // prints "42" for both call-by reference
                        // and call-by-value

相信我,我已经为Java编程了10年以上,并且在大学阶段教过比较编程语言课程。

链接地址: http://www.djcxy.com/p/20663.html

上一篇: Passing object to method in java appears to be by reference (and Java is by val)

下一篇: what is the difference between pass by reference and call by reference?