본문 바로가기

프로그래밍 언어 (プログラミング言語)/JAVA

자바에서 메모리를 절약하는 방법!!

메모리 누수(Leak)

자바에서 메모리 누수는 더 이상 사용되지 않는 객체들이 GC(가비지 컬렉션)에 의해 소멸되지 않고 누적되는 현상입니다.

가비지 컬렉션의 소멸 대상이 되려면 다른 Reference 변수에서 참조하고 있지 않아야 합니다.

 

1. 무의미하게 Wrapper Class를 만들지 말자!!

-> 예를 들어, int는 4byte이나 Integer는 20byte이다.

기본 자료형보다 Wrapper Class의 크기가 훨씬 크다. 고로, 무의미하게 Wrapper Class를 남발하지는 말자!

( Wrapper 클래스보다는 기본형 배열(레퍼번스 변수)을 사용하자!!!)

LinkedList<Integer> l = new LinkedList<>(); // 메모리 많이 잡아 먹음.

LinkedList<int [] > l = new LinkedList<>(); // 메모리 덜 잡아 먹음. 

l.add(new int [ ] { 2 } );

 

2. Map에 Immutable 데이터를 해제하지 않은 경우

Map에는 강력한 참조가 있어서, 내부 객체가 사용되지 않을 때도 GC 대상이 되지 않습니다.

즉, Map을 더이상 사용하지 않는다면, 메모리를 점유하고 있게 됩니다

즉, 데이터의 메모리를 해제하는 것이 바람직합니다.

WeakHashMap은 내부 데이터를 초기화할 수 있습니다.

 

3. Connection 사용 시 Try Catch 설계

아래의 경우 Connection을 생성했지만, try 내부에서 connection을 close하기 때문에, close가 실행되지 못합니다. 그래서 Connection이 열려있는 채로 메모리를 점유하게 됩니다.

try {
    Connection con = DriverManager.getConnection();
    // 예외 발생 !!!
    con.close();
} Catch(exception e) {
}

 

4. CustomKey 사용

Map을 사용할 때 custom key를 사용할 때는 equals()와 hashcode()를 값을 기반으로 구현해야합니다. 아래의 경우 Key값이 같은 객체로 인식하지 못해서 계속 Map에 쌓이게 되면서 메모리를 점유하게 됩니다.

public class CustomKey {
    private String name;
    
    public CustomKey(String name) {
        this.name=name;
    }
    
    public staticvoid main(String[] args) {
        Map<CustomKey,String> map = new HashMap<CustomKey,String>();
        map.put(new CustomKey("Shamik"), "Shamik Mitra");
   }
}

 

5. static 사용에 신중!!

1. Static 변수가 객체를 참조하고 있다면, 해당 객체는 GC에 의해 소멸되지 않습니다.

- Static 변수는 프로그램 종료 시점에 메모리가 반환되고, 사용하지 않아도 메모리를 점유하고 있습니다. 이런 static 변수를 재사용한다면 이점이 있지만, 사용하지 않으면 메모리를 점유하고 있게 됩니다. 

 

2. Stack에서 Heap에 있는 객체를 참조하고 있는 동안에는 해당 객체는 GC에 의해 소멸되지 않습니다.