JAVA/Thread

Thread 동기화 문제

반응형



Thread 동기화 문제

  • 스레드는 중앙의 리소스풀로 부터 빌린다스레드는 메모리파일 핸들소켓 등의 리소스를 공유하여 프로그램을  효율적으로 만단ㄷ 스레드가 동시에 같은 리소스를 사용하지만 않는다면 멀티 스레드 프로그램이  프로스스가별도의 리소스를 유지하는 멀티 프로세스 프로그램보다 훨씬 효율적이다.
  • 그러나 언제 어느 문장이 실행될지 몰라 결과의 순서를 예측할  없고자원을 공유하고 있을 경우 데드락 현상이 발생할  있다.
  • 스레드에 동일자원 접근에 대해 배타적인 접근을 할당해  방법은 Synchronized 명시해주는 방법이다.

예제)

Run(){

System.out.println(result);

}

 

Thread.start() 진행  System.out.println 자원을 서로 공유하기 때문에 출력에 문제가 발생   있다 문제는

Syncroized(){

Run(){

System.out.println(restul);

}

} 해결이 가능하다.

 

동기화의 단점

-> 단순히 synchronized 지정자를 모든 메소드에 추가하는 것만으로 동기화 문제를 해결   있는 것은 아니다.

  1. 가상머신에서 심각한 성능 저하가 발생한다.
  2. 데드락이 발생할 가능성이 급격히 높아진다.
  3. 동시 변경이나 접근으로 부터 보호하기 위해 항상 객체 자체를 보호해야하는 것은 아니고해당 메소드를 포함한 클래스의 인스턴스를 동기화 해도 실제 보호해야 하는 객체를 보호하지 못할  있다.

-> 이런 상황에서는 보호해야할 인스턴스 객체  자체를 동기화 하면 된다.

Synchronized(out) {

}

 

동기화를 피하는 방법

  1. 로컬 변수 사용(로컬 변수는 메소드가 실행   마다 가상 머신이 해당 메소드에 필요한 로컬 변수를 완전히 새로 만들기 때문에 동기화를 피할  있다.)
  2. 쓰레드에서 사용하고 있는 객체가 다른 곳에서 변하고 있을 경우  문제를 해결할  없다.

-> String 불변의 객체이기 때문에 사용하면 피할  있다. (Stringbuilder 아니다.) 이런 특징을 불변성이라고 하는데 불변성을 만들고 싶은 경우 private final 선언한다.

  1. Map, List, set 같은 콜렉션은 스레드로 부터 동기화를 피할  있다.(Collections.synchroizedSet(객체); 그러나 결구동시 실행을 위해서는 동기화가 필요 하다.

-> Collections.synchronizedList() 사용하여 리스트가 둉기화 중일 때도 리스트의 값들을 반복해서 순차적으로 접근하게   있다.

  1. 동기화를 너무 피하게 되면 결국에는 반환 받지 못하는 데드락 상태가 발생할  있다.(데드락이 발생하지 않게 유심히살펴보고 코드를  쓰는게 최선이다.)

 

데드락

-> 하염없이 자원을 서로 다른 스레드에서 기다리는 상태에 빠져버리는 것이 데드락 상태이다.

데드락 상태에 빠지지 않게 하기 위해서는 불필요한 동기화를 없애고 객체를 불변하게 사용하거나복사하여 사용하거나 아니면 로컬 변수로 사용한다.

반응형

'JAVA > Thread' 카테고리의 다른 글

Thread 크리티컬 세션  (0) 2016.12.21
java thread pool 소개  (0) 2016.12.21
JAVA 스레드 스케줄링  (0) 2016.12.21
JAVA Thread Futher, Callable, Executor  (0) 2016.12.21
Thread 폴링 방식  (0) 2016.12.21