Как увеличить значение класса Integer ссылки в Java из другого метода

NullPointerException s - исключения, возникающие при попытке использовать ссылку, которая указывает на отсутствие местоположения в памяти (null), как если бы она ссылалась на объект. Вызов метода по нулевой ссылке или попытка получить доступ к полю нулевой ссылки вызовет функцию NullPointerException. Они наиболее распространены, но другие способы перечислены на странице NullPointerException javadoc.

Вероятно, самый быстрый пример кода, который я мог бы придумать для иллюстрации NullPointerException, be:

public class Example {

    public static void main(String[] args) {
        Object obj = null;
        obj.hashCode();
    }

}

В первой строке внутри main я явно устанавливаю ссылку Object obj равной null. Это означает, что у меня есть ссылка, но она не указывает на какой-либо объект. После этого я пытаюсь обработать ссылку так, как если бы она указывала на объект, вызывая метод на нем. Это приводит к NullPointerException, потому что нет кода для выполнения в местоположении, на которое указывает ссылка.

(Это техничность, но я думаю, что она упоминает: ссылка, которая указывает на null, равна 't то же, что и указатель C, указывающий на недопустимую ячейку памяти. Нулевой указатель буквально не указывает на в любом месте , который отличается от указаний на местоположение, которое оказывается недопустимым.)

26
задан cchampion 5 February 2010 в 17:31
поделиться

7 ответов

Я не совсем уверен, что вы пытаетесь сделать здесь, но вы могли бы просто поддерживать хэш-таблицу со всеми ранее посещенными узлами, когда вы делаете свой широтный первый поиск глубины первый поиск.

-121--1592753-

Firebug ( https://addons.mozilla.org/en-US/firefox/addon/1843 ) или панель инструментов веб-разработчика ( https://addons.mozilla.org/en-US/firefox/addon/60 ). Оба показывают путь.

-121--1086947-

Нет, объекты не передаются по ссылке. Ссылки передаются по значению - есть большая разница. Целое число является неизменяемым типом, поэтому невозможно изменить значение в методе.

Ваш оператор n++; фактически является

n = Integer.valueOf(n.intValue() + 1);

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

EDIT: Ответ на запрос: это правильно. Предположительно, тип MyIntegerObj может изменяться и изменяет свое внутреннее состояние при вызове plusplus () . О, и не стоит искать способ реализации оператора - Java не поддерживает определяемые пользователем операторы.

37
ответ дан 28 November 2019 в 06:17
поделиться

Вы ищете что-то похожее на ссылку C ++ или параметр C # out. Java (и многие другие языки) не поддерживают это.

Этот тип поведения обычно достигается путем изменения метода с void на (в данном случае) int: public static int increment(int n) { return ++n; }

Если метод уже возвращает что-то, вы можете создать новый класс, который имеет два поля (могут быть даже открытыми): исходное возвращаемое значение и новое значение n.

Кроме того, вы также можете заключить целое число в общий класс Cell. Вам нужно написать этот класс Cell только один раз:

public class Cell<T> {
  public Cell(T t) { value = t; }
  public void set(T t) { value = t; }
  public T get() { return value; }
}

Затем вы можете использовать его во всех ситуациях, когда вы хотите использовать метод для изменения примитива:

public static void increment(Cell<Integer> n) {
  n.set(n.get()++);
}

Cell<Integer> n = new Cell<Integer>(0);
increment(n);
increment(n);
increment(n);
System.out.println(n.get()); // Output: 3
6
ответ дан Itay Maman 5 February 2010 в 17:31
поделиться

Как упоминал Джон Скит, все методы на Java являются проходными по значению, а не по ссылке. Поскольку типы ссылок передаются по значению, то внутри тела функции находится копия ссылки - и эта копия, и исходная ссылка указывают на одно и то же значение.

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

Но учтите, что на самом деле для того, чтобы делать то, что вы хотите, вам не нужна передача по ссылке. Например, вам не нужен метод для инкремента Integer - вы можете просто инкрементировать его в той точке в вашем коде, где он должен быть инкрементирован.

Для более сложных типов, таких как установка некоторого свойства на Объекте, объект, с которым вы работаете, скорее всего, мутируемый; в этом случае копия ссылки работает просто отлично, так как автоматическое разыменование приведет вас к оригинальному объекту, сеттер которого вы вызываете.

3
ответ дан 28 November 2019 в 06:17
поделиться

Вы можете использовать AtomicInteger из java.util.concurrent.atomic . У него есть метод incrementAndGet, который подходит для вашей витрины.

24
ответ дан 28 November 2019 в 06:17
поделиться

Замечание: по моему скромному мнению, запись n ++ для целочисленного объекта крайне ошибочна. Это основано на функции Java, называемой «автобоксинг», при которой примитивы преобразуются в соответствующие им объекты бокса - например, int в Integer или boolean в Boolean - автоматически и без предупреждения. Честно говоря, я считаю, что это плохая особенность. Да, иногда он упрощает вашу жизнь, автоматически выполняя удобное преобразование для вас, но он также может выполнять преобразования, которые вы не планировали и не подозревали, с непредвиденными побочными эффектами.

В любом случае, есть два способа выполнить то, что вы, по-видимому, пытаетесь сделать:

Первый: заставить функцию приращения вернуть новое целое число с обновленным значением. Например:

   public Integer increment(Integer n)
    {
      Integer nPlus=Integer.valueOf(n.intValue()+1);
    }

, затем вызовите его с помощью:

Integer n=Integer.valueOf(0);
n=increment(n); // now n==1
n=increment(n); // now n==2

И т. Д.

Два: создайте свой собственный класс, похожий на Integer, но изменяемый. Например:

class MutableInteger
{
  int value;
  public MutableInteger(int n)
  {
    value=n;
  }
  public void increment()
  {
    ++value;
  }
  ... whatever other functions you need ...
}

Конечно, большая загвоздка в том, что вам придется заново изобретать класс Integer.

3
ответ дан 28 November 2019 в 06:17
поделиться

Вы не можете. Java - это строго передача по значению.

См. http://javadude.com/articles/passbyvalue.htm

Вы можете заключить целое число в объект (или массив), передать его и обновить, вернуть значение или сделать целое число - переменная класса / экземпляра.

Что лучше, зависит от ситуации.

2
ответ дан 28 November 2019 в 06:17
поделиться

Целое число - это объект значения , что означает, что это значение не может измениться.

Обратите внимание, что n ++ эквивалентно n = n + 1 . Вы просто меняете значение, на которое ссылается локальная переменная n , а не значение самой n .

1
ответ дан 28 November 2019 в 06:17
поделиться
Другие вопросы по тегам:

Похожие вопросы: