В Java, как мы можем уничтожить экземпляр класса из метода внутри класса

Я подошел к нему аналогично случаю удаления любого обычного объекта, т. е. просто сделал ссылку null и позволил сборщику мусора выполнить свою работу.

однако для приравнивания к null в классе единственной ссылкой на объект является "this". Таким образом, код для следующего класса действителен:

class A{
  public A(){
    //Init
  }

  public void method destruct(){
    if(someCondition){
      this=null;  //Is this statement valid? Why / Why not?
    }
  }
}

14 ответов


this=null;  //Is this statement valid? Why / Why not?

это недопустимый Java, потому что this не lvalue-выражение, т. е. не то, что вы можете назначить. Это ошибка компиляции, как и 42 = i; ошибка компиляции.

(JLS говорит следующее о заданиях: " результатом первого операнда оператора присваивания должна быть переменная или возникает ошибка времени компиляции." - JLS 15.26.1 текст JLS затем переходит к списку различных вещей, которые квалифицируйте как переменные и this не является одним из них.)

кроме того, как duffymo говорит, это совершенно ошибочны, что нужно сделать в Java. Просто позвольте GC делать свою работу.


вы не" уничтожаете " объекты в Java. Это неправильно. Не делай этого.

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

вы, безусловно, должны сделать все возможное, чтобы убедиться, что вы не накапливаете и не держите ссылки без необходимости (например, слушатели в Swing).

но ваше предложение совсем не то. Прекратить и воздерживаться.


Примечание: то, что вы предлагаете, вряд ли окажется полезным.

вы можете использовать делегирование.

class A {
   private AImpl impl = new AImpl();

   public void close() {
      if (impl != null)
         impl.close();
      impl = null;
   }
}

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


прокси в некоторых контейнерах OSGi делают это при выгрузке компонента. Поскольку контейнер мало контролирует жизненный цикл ссылок, было бы сложно когда-либо выгружать библиотеку ( реализация.)


ваша цель-глубоко заблуждаются.

либо кто-то вне экземпляра содержит не слабую ссылку на него. Тогда он не будет собран независимо от того, что вы делаете внутри. Или никто не делает, тогда он в конечном итоге будет собран, независимо от того, что вы делаете внутри. В любом случае, this=null не имело бы значения, даже если бы это был законный java-код. Не делай этого. Если вас беспокоит время жизни объекта и истощение памяти, посмотрите на объект, от которого вы хотите избавиться.


задание this = null похоже на попытку сказать, что объект не ссылается на себя. Он всегда имплицитно ссылается на себя. Вам нужно найти, какие другие объекты могут ссылаться на этот и очистить их ссылки вместо этого. Обычно это происходит автоматически, поскольку большинство объектов сохраняются через локальные переменные, находящиеся в стеке. Когда я говорю "сохранено", я имею в виду, что на них ссылаются через цепочку ссылок, которая в конечном итоге приводит к переменной в стеке. Когда ты уйдешь ... метод, ссылка удаляется. Но если у вас есть статическая переменная, ссылающаяся на этот объект, это может быть случай, когда вы должны явно установить его null.


для сборщика мусора java, чтобы забрать ваш класс, он не должен ссылаться на другие классы.

заявление this=null; является незаконным, потому что левая сторона назначения должна быть переменной.


нет никакого способа явно delete в частности в Java. Java делает это, чтобы избежать зависания ссылок. Если ты ... --0--> объект, то другие объекты ссылаются на него потенциально может попытаться получить доступ к данным и получить ссылку на недопустимые данные.

вы не должны пытаться delete objects в любом случае, просто переместите все ссылки на объект в null.


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

рассмотрим другой подход к управлению памятью.


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


жизненный цикл объектов управляется JVM, по этой причине объект не может решить, когда он больше не нужен. Что вы можете сделать, это приложить некоторые усилия к ссылкам на этот объект. Тип ссылок может использоваться для указания на "важность" объекта.

основные типы ссылок на java можно найти здесь:

подробнее здесь: http://docs.oracle.com/javase/1.3/docs/api/java/lang/ref/package-summary.html

Обсуждение ссылок здесь: в чем разница между мягкой и слабой ссылки в Java? и понимание ссылочных классов Java: SoftReference, WeakReference и PhantomReference


вы можете по телефонам :

 System.gc() or RuntimeUtil.gc() from the jlibs

но если вы это сделаете, вы испортите среду выполнения JVM. Если вы установите refernce в null, объект все еще существует , его просто его ссылка не будет ссылаться на этот объект, и при следующем вызове GC он уничтожит объект(если другие ссылки не ссылаются на него).


нет приведенный выше код недействителен. Ссылка this класса длится только до тех пор, пока выполняется JVM. Настройка this == null будет infact дать вам ошибку компилятора, потому что хотя this называется ссылкой, Это фактически значение, и вы не можете ничего назначить to значение.

и это не нужно, так как this действителен только до тех пор, пока выполнение находится в этом коде, и GC не может претендовать на объект, который все еще выполняется. Однако, как только выполнение завершается для объекта,this также будет потерян, и объект автоматически станет доступным для GC (т. е. если нет другой ссылки на объект)


Это ошибка компиляции. Вы не можете присвоить NULL 'this'. Ключевое слово "this" может использоваться справа от equals (за исключением того, что левая рука не равна NULL. Причина: ничто не может быть присвоено значение null).

для уничтожения, в java, у вас есть GC, который может сделать эту работу для вас за кулисами.

обратите внимание, что для пользовательских объектов, вы все равно можете сделать что-то вроде -

object reference = null;

однако "это" нельзя использовать с левой стороны равняется.


сама причина, по которой поток выполнения находится внутри метода destruct (), говорит мне, что есть вызывающий объект, который содержит ссылку на этот экземпляр класса A. Поэтому, тем не менее, вы не можете сделать что - либо вроде "this = null" в java-это не помогло бы, хотя это было разрешено в java. Вы не можете уничтожить объекты в Java.