자바 효율 적 이 고 신축성 있 는 캐 시 만 들 기

2981 단어 자바
캐 시 를 쓰기 전에 다시 정렬 하 는 동시에 중복 쓰기 (두 스 레 드 를 동시에 기록) 를 방지 하거나 중복 읽 기 (기 존 스 레 드 기록, 계산 중, 다른 스 레 드 는 계속 접근 하지 않 고 결 과 를 기다 리 면 됩 니 다) 를 방지 해 야 합 니 다.
관건: 1 - Concurrent HashMap 세그먼트 잠 금.2 - Callable 시작 스 레 드, Future 대상 으로 돌아 갑 니 다.
코드:

public interface Computable {

    V compute(K arg)throws InterruptedException;

}


public class Memoizer implements Computable {

    private final Map> cache = new ConcurrentHashMap<>();
    private  Computable c=null;

    public Memoizer(Computable c) { this.c = c; }

    public V compute(final K arg) throws InterruptedException{

        while(true){
            Future f = cache.get(arg);
            if(f==null){
                Callable call = new Callable() {
                    @Override
                    public V call() throws InterruptedException {
                        return c.compute(arg);
                    }
                };
                FutureTask ft = new FutureTask(call);
                f = cache.putIfAbsent(arg,ft);
                if(f==null){
                    f = ft;
                    ft.run();
                }
            }
            try{
                return f.get();
            }catch (CancellationException e){
                cache.remove(arg,f);
            }catch(ExecutionException e){
                e.printStackTrace();
            }
        }

    }
}

분석: 다 중 스 레 드 상황 에서 효율 적 인 캐 시 를 만 들 려 면 먼저 캐 시 중복 쓰기 와 중복 읽 기 문 제 를 고려 해 야 합 니 다.중복 쓰기 1: Concurrent HashMap 을 이용 하여 중복 쓰 기 를 해결 하고 같은 key 덮어 쓰 기 를 해결 하 는 동시에 세그먼트 잠 금 segment 가 더욱 정교 하고 데이터 동기 화 에 유리 합 니 다.2: 쓰기 전에 cache. get (arg) 에 스 레 드 가 기록 되 어 있 는 지 확인 합 니 다.3: Concurrent HashMap 을 통 해 cache. puutIfAbsent (arg, ft) 방법 을 기록 하지 않 고 원자 기록 (두 스 레 드 가 동시에 기록 되 는 것 을 방지 합 니 다.) 4: 기록 되면 계산 이 진행 되 기 를 기다 리 고 있 습 니 다. f. get () 은 결 과 를 되 돌 릴 때 까지 차단 상태 에 있 습 니 다.
교육 을 받 는 것 과 을 설명 하 다.

좋은 웹페이지 즐겨찾기