>  기사  >  Java  >  Java에서 '약한' 참조가 무엇인지 살펴보겠습니다.

Java에서 '약한' 참조가 무엇인지 살펴보겠습니다.

coldplay.xixi
coldplay.xixi앞으로
2021-01-06 18:10:212493검색

java basic tutorialcolumn은 Java "약한" 참조

Java에서 '약한' 참조가 무엇인지 살펴보겠습니다.

권장(무료): java basic tutorial

객체 obj가 Java에서 생성되면 힙. GC가 실행되어 obj를 가리키는 참조가 없음을 발견하면 obj 개체의 힙 메모리 공간이 회수됩니다.

즉, 객체를 재활용하려면 두 가지 조건이 충족되어야 합니다.

(1) 해당 객체를 가리키는 참조가 없습니다.

(2) GC가 실행됩니다.

실제 개발에서는 다음과 유사하게 객체에 대한 모든 참조 지점을 비워서 다음에 GC가 실행될 때 객체가 재활용되도록 할 수 있습니다.

Object c = new Car();    
c=null;

그러나 이렇게 하면 매우 번거롭고 위반합니다. GC에 관한 것입니다. 자동 재활용 원리. 간단한 경우에는 프로그래머가 수동으로 설정할 필요가 없습니다. Java에서는 간단한 개체의 경우 이를 호출하는 메서드가 실행될 때 이를 가리키는 참조가 스택에서 팝되어 다음 번에 재활용되기 때문입니다. GC 실행.

그러나 캐시를 사용할 때 특별한 예외가 있습니다. 캐시에 있는 개체는 프로그램이 실행되는 동안 정확하게 프로그램을 실행하는 데 필요한 것이므로 캐시에 있는 참조는 GC가 소유하지 않습니다. 즉, 캐시의 참조) 기본 프로그램과 동일한 수명 주기) 그러면 캐시에 참조가 많아질수록 GC에서 재활용할 수 없는 객체도 늘어나고 자동으로 재활용될 수도 없습니다. 이러한 개체를 재활용해야 하는 경우 이러한 개체를 재활용하는 작업은 프로그래머에게만 맡길 수 있습니다. 그러나 이는 GC(재활용 가능한 객체의 자동 재활용)의 본질에 어긋납니다.

그래서 java에는 약한 참조가 도입되었습니다.

Object c = new Car(); //只要c还指向car object, car object就不会被回收 -->(强引用)

다른 강한 참조 없이 약한 참조로만 개체를 ​​가리키는 경우 GC가 실행되면 개체가 재활용됩니다.

다음은 인터넷의 예입니다. 먼저 엔터티 클래스를 정의합니다.

public class Car {
    private double     price;
    private String    color;

    public Car(double price, String color)
    {
        this.price = price;
        this.color = color;
    }

    public double getPrice()
    {
        return price;
    }

    public String getColor()
    {
        return color;
    }

    public String toString()
    {
        return "This car is a " + this.color + " car, costs $" + price;
    }
}

일반적으로 WeakReference를 사용할 때 클래스는 WeakReference에서 상속되도록 정의되며 이 클래스에는 다른 속성이 정의되지 않습니다. :

public class WeakReferenceCar extends WeakReference<Car>
{
    public WeakReferenceCar(Car car)
    {
        super(car);
    }
}

메인 함수를 호출하세요. 물론 GC의 효과를 더 명확하게 보려면 가상 머신 매개변수 "-XX:+PrintGCDetails"를 설정하세요.

public static void main(String[] args)
{
    Car car = new Car(2000.0, "red");
    WeakReferenceCar wrc = new WeakReferenceCar(car);
    wrc.setStr("111");
    int i = 0;
    while (true)
    {
        if (wrc.get() != null)
        {
            i++;
            System.out.println("WeakReferenceCar's Car is alive for " + i + ", loop - " + wrc);
        }
        else
        {
            System.out.println("WeakReferenceCar's Car has bean collected");
            break;
        }
    }
}

마지막은 실행 결과입니다

WeakReferenceCar's Car is alive for 68450, loop - interview.WeakReferenceCar@776ec8df
WeakReferenceCar's Car is alive for 68451, loop - interview.WeakReferenceCar@776ec8df
WeakReferenceCar's Car is alive for 68452, loop - interview.WeakReferenceCar@776ec8df
WeakReferenceCar's Car is alive for 68453, loop - interview.WeakReferenceCar@776ec8df
[GC (Allocation Failure) [PSYoungGen: 34304K->1000K(38400K)] 34320K->1016K(125952K), 0.0015129 secs] [Times: user=0.02 sys=0.02, real=0.00 secs] 
WeakReferenceCar's Car is alive for 68454, loop - interview.WeakReferenceCar@776ec8df
WeakReferenceCar's Car has bean collected
Heap
PSYoungGen      total 38400K, used 1986K [0x00000000d5e00000, 0x00000000da900000, 0x0000000100000000)
eden space 33280K, 2% used [0x00000000d5e00000,0x00000000d5ef6b70,0x00000000d7e80000)
from space 5120K, 19% used [0x00000000d7e80000,0x00000000d7f7a020,0x00000000d8380000)
to   space 5120K, 0% used [0x00000000da400000,0x00000000da400000,0x00000000da900000)
ParOldGen       total 87552K, used 16K [0x0000000081a00000, 0x0000000086f80000, 0x00000000d5e00000)
object space 87552K, 0% used [0x0000000081a00000,0x0000000081a04000,0x0000000086f80000)
Metaspace       used 3547K, capacity 4564K, committed 4864K, reserved 1056768K
class space    used 381K, capacity 388K, committed 512K, reserved 1048576K

68454 루프 후에 WeakReferenceCar와 관련된 개체 Car가 재활용된 것을 볼 수 있습니다. 약한 참조 자체 wrc가 아니라 약한 참조와 관련된 개체 자동차가 재활용된다는 점에 유의하세요.

WeakReference의 특징 중 하나는 언제 재활용될지 불확실하다는 것입니다. 이는 GC 작업의 불확실성에 따라 결정되기 때문입니다. 따라서 일반적으로 약한 참조에서 참조하는 개체는 가치 있고 캐시되며 쉽게 개체를 캐시할 수 있습니다.

약한 참조가 가리키는 객체가 재활용된 후에는 약한 참조 자체가 실제로 쓸모가 없습니다. Java는 객체가 가리키는 참조를 저장하기 위해 ReferenceQueue를 제공합니다. 사용법은 WeakReference를 정의할 때 ReferenceQueue 객체를 생성자에 매개변수로 전달하는 것입니다.

위 내용은 Java에서 '약한' 참조가 무엇인지 살펴보겠습니다.의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

성명:
이 기사는 segmentfault.com에서 복제됩니다. 침해가 있는 경우 admin@php.cn으로 문의하시기 바랍니다. 삭제