자바 웹 개발자가 될거야/JAVA

[JAVA] 동기화 메소드 / synchronized

whitz 2021. 12. 9. 11:17

 

< 동기화 메소드 >

 

- 멀티 스레드 프로그램에서 단 하나의 스레드만 실행할 수 있도록 임계 영역을 지정한 것을 말한다

- 사용 중인 객체를 다른 메소드가 변경할 수 없게 함

 

 

① synchronized

 

- 동기화 메소드를 만들려면 synchronized 키워드 붙이면 됨- 인스턴스와 정적 메소드 어디든 붙일 수 있음

 

public synchronized void method(){
	임계영역 // 단 하나의 스레드만 실행
}

 

- 스레드가 동기화 메소드를 실행하는 즉시 객체 잠금일어나고 스레드가 동기화 메소드 실행 종료하면 잠금 풀림

- 동기화 메소드가 여러 개일 경우, 한 스레드 실행할 때 다른 동기화 메소드 실행할 수 없지만 일반 메소드는 실행 가능

 

 

② 예제

 

- 동기화하지 않으면 객체가 공유되면서 결과값이 다른 스레드에 의해 영향을 받을 수 있다.

 

public class MainThreadExample {

	public static void main(String[] args) {
		Calculator calculator = new Calculator();
		
		User1 user1 = new User1();
		user1.setCalculator(calculator);
		user1.start();
		
		User2 user2 = new User2();
		user2.setCalculator(calculator);
		user2.start();	

	}
}
public class Calculator {
	private int memory;
	
	public int getMemory() {
		return memory;
	}
	
	public void setMemory(int memory) {
		this.memory = memory;
		try {
			Thread.sleep(2000);
		}catch(InterruptedException e) {}
		System.out.println(Thread.currentThread().getName()+": "+this.memory);
	}
}
public class User1 extends Thread{
	private Calculator calculator;
	
	public void setCalculator(Calculator calculator) {
		this.setName("User1");
		this.calculator=calculator;
	}
	
	@Override
	public void run() {
		calculator.setMemory(100);
	}
}
public class User2 extends Thread{
	private Calculator calculator;
	
	public void setCalculator(Calculator calculator) {
		this.setName("User2");
		this.calculator = calculator;
	}
	
	@Override
	public void run() {
		calculator.setMemory(50);
	}
}

 

 

  · 동기화하지 않아서 User1이 원래 100이 나와야하는데 User2 영향으로 User2 스레드가 저장한 50을 출력하게 된다

 

- setMemory를 동기화 해보겠다

 

public class Calculator {
	private int memory;
	
	public int getMemory() {
		return memory;
	}
	
	public synchronized void setMemory(int memory) {
		this.memory = memory;
		try {
			Thread.sleep(2000);
		}catch(InterruptedException e) {}
		System.out.println(Thread.currentThread().getName()+": "+this.memory);
	}

}

 

 

  · 정상적으로 User1은 100을 출력하게된다

   · 안정성은 보장되지만 효율은 낮아진다