我已经阅读了Jon Skeet的[excellent] article关于在Java中传递值的信息,并且在同一主题上看到了this question。我相信我了解他们,但我仍然
想知道返回值。

当一个对象被返回时(如从一个吸气剂中返回),然后在其原始范围(从中获取它)中进行了更改,该对象引用被该获取器的返回值分配给的变量所拥有吗?满口的男孩..
举一个例子:

public class Dog {

    String dog ;

    public String getName()
    {
        return this.dog;
    }

    public Dog(String dog)
    {
        this.dog = dog;
    }

    public void setName(String name)
    {
        this.dog = name;
    }

    public static void main(String args[])
    {
        Dog myDog = new Dog("Rover");
        String dogName = myDog.getName();
        myDog.setName("Max");
        System.out.println(dogName);
    }
}


是否打印Rover或Max?

更新
是否打印流动站。

我最初的问题的答案很好,但理查德·廷格(Richard Tingle)在下面的评论中添加了很多有用的信息,因此我认为我将为后代提供测试课程。

public class Foo {
    private ArrayList<Integer> arrayList;

    public Foo() {
        arrayList = new ArrayList<Integer>();
        arrayList.add(1);
        arrayList.add(2);
        arrayList.add(3);

    }

    public ArrayList<Integer> getArrayList() {
        return arrayList;
    }

    public void addToArrayList(int item) {
        arrayList.add(item);
    }

    public static void main(String args[]) {
        Foo foo = new Foo();
        ArrayList<Integer> arrayList = foo.getArrayList();
        ArrayList<Integer> cloneList = (ArrayList<Integer>)foo.getArrayList().clone();
        System.out.println(arrayList.contains(4));
        System.out.println(cloneList.contains(4));
        foo.addToArrayList(4);
        System.out.println(arrayList.contains(4));
        System.out.println(cloneList.contains(4));
}


输出为falsefalsetruefalse

最佳答案

如许多答案所述,将打印“ Rover”,因为您已更改了dog中的实际字符串。您尚未更改String本身(由于String是不可变的,又称为不可更改,因此您无法执行此操作)。

public static void main(String args[])
{
    Dog myDog = new Dog("Rover"); //myDog contains STRING1 ("Rover")
    String dogName = myDog.getName(); //dogName is set to refer to STRING1 ("Rover")
    myDog.setName("Max"); //myDog name set to STRING2 ("Max") (STRING1 unaffected)
    System.out.println(dogName); //dogName still refers to STRING1 ("Rover"), "rover" printed
}


更一般的概念

这可能给人的印象是,一旦使用吸气剂从另一个对象检索内部对象,它就完全独立了,您可以根据需要进行更改。并非总是如此。字符串是不可变的,因此您无法更改其内部状态。但是,如果您访问了一个可变的对象(也可以更改),并且在Dog对象外部更改了其内部状态,则它仍然会影响Dog对象的内部状态。我将使用ArrayList展示此概念

public class Dog {

    public ArrayList<String> names=new ArrayList<String>();

    public ArrayList<String> getNames() {
        return names;
    }

    public void setNames(ArrayList<String> names) {
        this.names = names;
    }

    public static void main(String[] args){
         Dog dog=new Dog();
         dog.getNames().add("Rover");

         ArrayList<String> someArrayList=dog.getNames();
         someArrayList.add("Rex");

         System.out.println(dog.getNames().contains("Rex")); //prints true. dog's internal state effected from afar

         someArrayList=new ArrayList<String>(); //change someArrayList to refer to a whole new ArrayList
         someArrayList.add("bad");

         System.out.println(dog.getNames().contains("bad")); //prints false, someArrayList now points to a different ArrayList to the one internal to dog

    }

}


如您所见,如果您检索到arrayList,然后向其添加对象,这将影响Dog中的ArrayList。如果您检索arrayList并将变量设置为完全不同的ArrayList,则这不会影响Dog中的arrayList(因为它的数组ArrayList不同)。将对象视为“没有特别的地方”,并将变量寻址到这些对象。

如此类推;您(Dog对象)有一个您关心的房屋(其他对象)的通讯录。您可以将地址簿更改为指向另一所房子,没有人会在意。但是,如果您在写给房子的信中说“将门漆成绿色”,则其他人对该房子的地址都会注意到。

一般规则是,如果您更改变量以使其仅指向更改该变量的对象(例如更改地址簿中的地址),则该变量始终包含=且可能包含new(但可能不包含新的字符串被隐藏)。另一方面,如果您在对象上使用方法(例如,将包裹发送到您有地址的房屋),则该对象可见的任何地方都将看到更改(这始终涉及到方法的. setter(或以其他方式更改对象,例如add))

关于java - Java返回值,对象引用,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/23383303/

10-11 23:20
查看更多