레이블이 Java인 게시물을 표시합니다. 모든 게시물 표시
레이블이 Java인 게시물을 표시합니다. 모든 게시물 표시

2011년 1월 7일 금요일

LinkedHashmap LRU Caching

LinkedHashMap의 생성자 중 LinkedHashMap(int capacity, float loadFactor, boolean accessOrder)가 있다.
capacity는 생성할때 map의 크기를 얼마로 할 것인가가 되고
loadFactor는 capacity의 몇 %가 차게되면 용량을 늘려야 할것인가
마지막 불리언 값은 정렬을 삽입 순서(false)냐 접근 순서(true)냐에 대한 인자이다.

그리고 맵에 put이 호출되면 엔트리를 생성해서 addEntry하게 되고
LinkedHashMap의 addEntry는 마지막에 removeEldestEntry를 호출하고 이 리턴이 true이면 정렬 순서의 첫 값을 삭제한다.

LRU 방식으로 특정한 크기의 자료를 유지하고 싶을때 이를 이용하면 된다.

import java.util.LinkedHashMap;
import java.util.Map;



public class LRUCache<K, V> extends LinkedHashMap<K, V>
{
    private static final long serialVersionUID = 734283243247234L;
    private final int         maxSize_;



    public LRUCache(final int maxSize)
    {
        super((maxSize + 1) * 4 / 3 + 1, .75f, true); // <-- 0.75의 load factor가 매직 넘버처럼 쓰인다.
        this.maxSize_ = maxSize + 1;
    }



    @Override
    protected boolean removeEldestEntry(final Map.Entry<K, V> eldest)
    {
        return this.size() >= this.maxSize_;
    }
}

주의해야 할 점은 capacity의 값이다. capacity의 75%가 차게 되면 capacity의 2배 증가와 re-hashing이 발생한다. max 값으로 크기가 고정 될 것이므로 굳이 용량 증가나 re-hashing을 일으킬 필요가 없으므로
용량을 max값의 4/3 크기로 한다.
또 입력받은 maxSize에 1을 더한 값으로 임계치를 정한 것은 LinkedHashMap에서 size >= threshold 조건에 걸릴때 용량 resize를 하기 때문에 입력 받은 max에 1을 더한 값과 비교하도록 한 것이다.

2010년 12월 7일 화요일

java logging

기본 자바 환경에서 logger를 설정하고 아무리 logger의 level을 변경해봐야 소용없다.
일단 console handler의 레벨이 INFO이기 때문에 console handler의 레벨을 변경해야 하고
console handler를 새로 생성해서 addHandler로 등록해서 사용할 경우 로그가 두번씩 찍히고
logger의 핸들러를 getHandlers로 얻어와 변경하려해도 0개를 리턴한다.



        if (logger.getUseParentHandlers()) {
            Logger parentLogger = logger.getParent();
            Handler[] handlers = parentLogger.getHandlers();
            for (Handler handler : handlers) {
                if (handler instanceof ConsoleHandler)
                    handler.setLevel(Level.ALL);
            }
        }
        else {
            Handler[] handlers = logger.getHandlers();
            for (Handler handler : handlers) {
                if (handler instanceof ConsoleHandler)
                    handler.setLevel(Level.ALL);
            }
        }

2010년 10월 21일 목요일

Java Naming Convention

아주 오래전에 읽었봤었지만 그때는 중요성도 모르고 그저 그런가보다 하고 지나갔던 코딩컨벤션
특히 네이밍이 코딩에서 가장 어려운 일이라는 걸 느껴본 사람이라면 다시 한번 보시길...
http://geosoft.no/development/javastyle.html
가장 중요한 말은 이 모든 규칙들은 가독성을 위해서라면 위반되어도 된다는 말.
  1. 필드는 ‘_’ 접미사를 사용한다.
  2. 변수의 길이는 영역과 비례한다.
  3. 객체명의 의미를 메소드명에 넣지마라.
line.getLength(); // NOT: line.getLineLength
  4. compute, find, initialize 사용
  5. 컬렉션은 복수형으로
  6. 개수를 나타내는 변수는 ’n’ 접두사를 사용한다.
  7. 엔터티 번호에는 ‘i’ 접두사나 ‘No’ 접미사를 사용한다.
  8. 대응하는 단어를 사용한다.
get/set , add/remove , create/destroy , start/stop , insert/delete , increment/decrement , old/new , begin/end , first/last , up/down , min/max , next/previous , old/new , open/close , show/hide , suspend/resume        
  9. 함수명은 ‘처리 후 무엇을 리턴하는지’, 프로시저명은 ‘무엇을 처리하는지’를 나타낸다.
  10. 인터페이스 디폴트 구현은 ‘Default’ 접두사를 사용한다.
  11. 팩토리 메소드의 이름은 ‘new’ 접두사에 반환하는 인스턴스의 클래스명으로 한다.
public Point newPoint(...)
  12. 메소드 선언 규칙은 <access> static abstract synchronized <unusual> final native 순서이다.
  13. do-while 사용 자제
  14. 조건이 복잡한 경우 임시 boolean으로 단순화 한다.
  15. 정상적인 경우를 if에 놓고 예외를 else에 둔다.
  16. 조건문과 한줄에 놓지 마라.
디버깅을 위해서
  17. 조건문 안에 실행문이 있어서는 안된다.
  18. 특정 의미를 갖는 숫자는 항상 의미를 나타내는 상수로 바꿔서 사용한다.
  19. 빈 for문은 ‘;’(세미콜론)을 새 줄에 놓는다.
for(<initialization>; <condition>; <update>)
 ;
  20. 복잡한 메소드는 주석을 달지 말고 새로 만든다.(self-documenting)
  21. javadoc주석을 제외한 주석은 multi-line 주석이라고 해도 ‘//‘를 사용한다.
/* */주석은 디버깅용으로 언제든 제거해서 사용 할 수 있게 한다.
  22. 컬렉션은 포함하는 유형을 주석으로 뒤에 넣는다.
private Vector points_; // of Point
  23. 모든 public 클래스, 또 publics 클래스내의 public, protected 메소드는 javadoc을 만든다.
Java naming은 아니지만 참고할만한 http://msdn.microsoft.com/en-us/library/xzf533w0(v=VS.71).aspx

2010년 5월 24일 월요일

static logger

logger 선언시 final static이 좋을까 그냥 final이 좋을까 고민을 한다면
참고하시라...
http://wiki.apache.org/commons/Logging/StaticLog

2009년 11월 18일 수요일

인스턴스 초기화 블럭

기본값 -> 명시적초기화 -> 인스턴스 초기화 블럭 -> 생성자
의 순서로 된다고 했으나 조심할 것은
부모생성자->인스턴스초기화블럭->자신의생성자
이다.