본문 바로가기
Tech/Java

Java Synchronized을 이용한 트랜잭션 예제

by Augustine™ 2018. 4. 26.
반응형

Java Synchronized(동기화)란 여러 개의 Thread가 한 개의 자원을 사용하고자 할 때, 

해당 Thread만 제외하고 나머지는 접근을 못하도록 막는 것이다.

이를 응용해서, 은행 ATM 의 Transaction 예를 만들어보자.


시나리오

1. User01이 ATM에서 돈을 인출하려 함.

2. User02가 User01이 인출하고 있는 도중에, 돈을 인출할 수 없어야 함.

3. User01의 인출이 끝날때 까지 기다려야 함.

* 인출의 행위는 Thread간 상호 배타적으로 동작해야 함.


package com.augustine.threadtest3;

import java.util.concurrent.atomic.AtomicInteger;

class SyncThreadTest {
	public static void main(String args[]) {
		Runnable r = new SyncRunnable();
		new Thread(r, "User01").start(); 
		new Thread(r, "User02").start(); 
	}
}

class Account {
	//private int balance = 1000;
	private AtomicInteger balance = new AtomicInteger(1000);

	public  int getBalance() {
		return balance.get();
	}

	//ATM에서 인출의 행위는 synchronized를 사용하여, Thread 간 해당 행위를 배타적으로 만든다.
	public synchronized boolean withdraw(int money){
		boolean result = false;
		if(balance.get() >= money) {
			try { Thread.sleep(1000);} catch(InterruptedException e) {}
			//balance -= money;
			balance.set(getBalance()-money);
			result =  true;
		}
		return result;
	} 
}

class SyncRunnable implements Runnable {
	Account acc = new Account();

	public void run() {
		while(acc.getBalance() > 0) {
			int money = (int)(Math.random() * 3 + 1) * 100;
			boolean result = acc.withdraw(money);
			if (result) {
				System.out.println(Thread.currentThread().getName()+"이"+money +"원을 출급하여 " +acc.getBalance()+"원 남았어요.");
			} else {
				System.out.println(Thread.currentThread().getName()+"이 "+money +"원 출급은 거부되었어요.. 잔액 : " +acc.getBalance()+"원 ");
			}
		}
	} // run()
}


반응형

'Tech > Java' 카테고리의 다른 글

Java collection - Set  (0) 2018.05.09
JVM의 메모리 구조  (0) 2018.05.04
Thread 예제  (0) 2018.04.25
List<Object>를 List<Long>로 변환  (0) 2017.02.21
Error 1723. (JDK 삭제 오류)  (0) 2017.01.11

댓글