Как можно назначить Java для указания объекта вместо создания копии?

В классе у меня есть:

private Foo bar;
public Constructor(Foo bar)
{
    this.bar = bar;
}

Вместо того, чтобы создавать копию бара из объекта, предоставленного в параметре, можно ли включить указатель в bar в конструкторе, чтобы изменить исходную панель, изменив поле в этом объекте?

Другой способ:

int x = 7;
int y = x;
x = 9;
System.out.print(y); //Prints 7.

Можно настроить его так, чтобы печать y печатала 9 вместо 7?

Ответ 1

Ваш последний пример работает так, потому что int является примитивным, он копируется по значению. В первом примере "this.bar" будет содержать копию ссылки (вид указателя) в bar. Поэтому, если вы измените исходную панель (внутренне), изменение будет отражено в вашем классе. Попробуйте.

Ответ 2

Когда переменная используется в качестве аргумента для метода, содержимое всегда копируется. (Java имеет только call-by-value.) Важно то, что вы можете ссылаться только на объекты через ссылки. Итак, что на самом деле происходит при передаче переменной, ссылающейся на объект, является то, что вы передаете ссылку на объект (по значению!).

Кто-то может сказать вам, что "примитивы передаются по значению", а "не примитивы передаются по ссылке", но это просто потому, что переменная никогда не может содержать объект для начала, а только ссылку на объект. Когда кто-то это поймет, он согласится, что даже переменные, относящиеся к объектам, передаются по значению.

Из Является ли Java "pass-by-reference " или" пропуск по значению",

Java всегда передается по значению. Трудно понять, что Java передает объекты в качестве ссылок, переданных по значению.

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

Java манипулирует объектами по ссылке, и все переменные объекта являются ссылками. Однако Java не передает аргументы метода по ссылке; он передает их по значению.

В Java нет примитивной части для ссылочного типа С++ для примитивов.

Ответ 3

Чтобы получить это поведение, вы можете изменить член объекта:

public class Number{
  int value;
  Number(int value){
    this.value = value;
  }
  public String toString() {
    return "" + value;
  }
}

Затем вы можете:

Number x = new Number(7);
Number y = x;
x.value = 9;
System.out.println(y);//prints 9

Ответ 4

Java никогда не копирует объекты. Легче всего думать, что для каждого "нового" у вас будет один экземпляр объекта - никогда больше.

Люди получают ДЕЙСТВИТЕЛЬНОЕ ОБЕСПЕЧЕНИЕ, когда они обсуждают это с точки зрения прохождения по ссылке/переходу по значению, если вы не удивительно знакомы с тем, что означают эти термины, я предлагаю вам игнорировать их и просто помнить, что Java никогда не копирует объекты.

Итак, java работает точно так, как вы хотели, чтобы ваш первый пример работал, и это основная часть OO Design - тот факт, что как только вы создали экземпляр объекта, это тот же объект для всех, кто его использует.

Работа с примитивами и ссылками немного отличается - поскольку они не являются объектами, которые они всегда копируют, но чистый эффект заключается в том, что java почти всегда делает то, что вы хотите, чтобы он делал без дополнительного синтаксиса или путаницы.

Ответ 5

Чтобы сохранить исходное значение панели элементов, вам необходимо реализовать интерфейс Cloneable. Затем перед назначением нового значения объекту вам нужно будет сделать клон и передать клонированное значение и назначить новые значения клонированному объекту. Вот учебник о том, как это сделать http://www.java-tips.org/java-se-tips/java.lang/how-to-implement-cloneable-interface.html.