. NET 에서 의 지연 로드

3460 단어 .net
응용 프로그램 에서 많은 실례 가 생 성 대상 을 지연 시 킬 수 있 습 니 다. 예 를 들 어 디자인 모드 의 단일 모드 는 매우 흔히 볼 수 있 는 상황 입 니 다. 라인 안전 을 고려 하지 않 으 면 다음 과 같은 코드 를 작성 합 니 다.
public class SingleInstance
{
    private static SingleInstance instance;
    private SingleInstance()
    {   
    }
    
    public static SingleInstance Instance
    {
        get
        {
            if (instance == null)
            {
                instance = new SingleInstance();
            }
            
            return instance;
        }
    }
}

다 중 스 레 드 환경 에서 실행 할 수 있 도록 하려 면 double check 방식 으로 스 레 드 간 에 여러 개의 예제 가 생 성 되 지 않도록 업그레이드 합 니 다. 코드 는 다음 과 같 습 니 다.

public class SingleInstance { private static SingleInstance instance; private static object lockObj = new Object(); private SingleInstance() { } public static SingleInstance Instance { get { if (instance == null) { lock (lockObj) { if (instance == null) { instance = new SingleInstance(); } } } return instance; } } }


이 코드 는 정말 스 레 드 가 안전 한 것 이 아 닙 니 다. IA64CPU 구조 상 null 로 돌아 갈 가능성 이 있 기 때문에 키워드 volatile 을 사용 하여 intance 대상 (volatile 의 역할 은 메모리 울타리 fence 추가) 을 수식 하면 코드 가 변 합 니 다.
public class SingleInstance
{
    private static volatile SingleInstance instance;
    private static object lockObj = new Object();
    private SingleInstance()
    {   
    }
    
    public static SingleInstance Instance
    {
        get
        {
            if (instance == null)
            {
                lock (lockObj)
                {
                    if (instance == null)
                    {
                        instance = new SingleInstance();
                    }
                }
            }
            
            return instance;
        }
    }
}

보기 에는 괜 찮 은 것 같 습 니 다. 다만 코드 가 좀 길 어 졌 습 니 다.. NET 은 우리 에 게 레이 지 를 제공 해 주 었 습 니 다.
대상 은 이러한 대상 을 만 드 는 메커니즘 을 해결 해 주 었 습 니 다. 수정 후 코드 는 다음 과 같 습 니 다.
public class SingleInstance
{   
    private static Lazy<SingleInstance> SingleInstanceFacotry = new Lazy<SingleInstance>(()=> new SingleInstance(), true);   
    
    private SingleInstance()
    {   
    }
    
    public static SingleInstance Instance
    {
        get
        {
            return SingleInstanceFacotry.Value;
        }
    }
}

Lazy
의 구조 함수 에서 스 레 드 안전 이 필요 한 지 편리 하 게 설정 할 수 있 습 니 다.
이렇게 매번 Lazy 가 있어 야 돼 요.
보조 적 으로... NETBCL 의 설계 자 는 또 다른 모델 을 제공 했다. Lazy Initializer 를 사용 하여 스 레 드 가 안전 하 다 는 것 을 확보한다. 예제 코드 는 다음 과 같다.
public class SingleInstance
{   
    private static SingleInstance instance;
    
    private SingleInstance()
    {   
    }
    
    public static SingleInstance Instance
    {
        get
        {
            LazyInitializer.EnsureInitialized(ref instance, ()=> new SingleInstance());
            return instance;
        }
    }
}

이런 방식 의 장점 은 원래 의 비 스 레 드 안전 에서 스 레 드 안전 업데이트 코드 가 가장 적 다 는 것 이다.

좋은 웹페이지 즐겨찾기