CH04 - Locks
Dead Lock 예제 StackOverflow
functionOne()에서 functionTwo()를 호출 순간 dead lock
이유: the thread would have to wait for the lock...which it holds itself.
public synchronized void functionOne() {
// do something
functionTwo();
// do something else
// redundant, but permitted...
synchronized(this) {
// do more stuff
}
}
public synchronized void functionTwo() {
// do even more stuff!
}Dead Lock 해결방법 - ReentrantLock
ReentrantLockReentrant Mutex (a.k.a, Recursive Mutex)
동일한 쓰레드에서 여러번 락을 걸 수 있음
lock 개수만큼 unlock을 해야된다.
예제에서,
addPotato()에서addPotato()으로 갈때 각 메소드에서 lock 2번과 unlock을 2번한다.
자바의 Lock을 구현한 3개 클래스
ReentrantLockReentrantReadWriteLock.ReadLockReentrantReadWriteLock.WriteLock전부 이름에 ReentrantLock이 포함됨. 즉, 자바에선 non-ReentrantLock는 지원안함.
코드해석
addPotato()에 동일 쓰레드에 있는addGarlic()을 호출하여, 데드락 위험이 있지만,ReentrantLock사용하여 해결
Try Lock 사용 유무 비교
Mutex (pencil) 를 얻으려고 스탠다드 Lock 사용 경우
아래 코드 "★★★★여기★★★★★" 를 보면, 다른 사람이 적는 시간 3초를 기다리게 된다.
효율적으로 가려면, Thinking 시간이 1초이기 때문에 3번 Thinking 해서 다른 사람의 Writing이 끝나면 적으면, 더 빨리 끝낼 수 있다.
Try Lock 사용한 경우
Lock.tryLock()속도가 빠르다. (걸린시간 결과 확인하기)
이유
pencil.tryLock()을 보면try 해보고, 이미 lock이 걸려있으면, return false 한다.
교훈
다른 쓰레드가 사용중인 자원이 필요할 경우, 마냥 기다리지 말고, 다른일을 먼저 처리해도 되면 그걸 하고 와서 다시 기다려보자.
ReentrantReadWriteLock
Reader-Writer Lock 특징
Shared Read: 여러 쓰레드가 같이 읽을 수 있음
Exclusive Write: 한 쓰레드만이 쓸 수 있음
보통은 일반적은 DB 처럼 Read가 많음. (Write많으면, Reader-Writer Lock 쓸 필요 없음.)
코드 해석
10명의 Reader와 2명의 Writers가 캘린더를 공유한다.
Reader-Writer Lock을 사용하지 않았을때 나타나는 문제점을 본다.
Read와 Writer Lock을 분리한다.
위 두개 결과 비교
첫번째 코드 결과
문제점: 한 reader가 읽는 동안 다른 reader도 읽을 수 있어야 하는데, 쓸데없이 한 리더가 자원을 계속 점유한다.
궁금: 왜 7번보다 훨씬 많이 나오지...? 예를들어, 첫번째 "Reader-2 sees that today is Sun"이게 30번은 나옴..
두번째 코드 결과
결과 값이 짧다.
Reader가 고르게 자원을 공유하는 것을 확인할 수 있다.
getReadLockCount()를 통해 현재 같이 read 중인 (=같이 Lock를 holding 중인) 다른 쓰레드를 확인할 수 있다.
QUIZ
How many threads can possess the ReadLock while another thread has a lock on the WriteLock?
0
What is the maximum number of threads that can possess the WriteLock of a ReentrantReadWriteLock at the same time?
1
What is the maximum number of threads that can possess the ReadLock of a ReentrantReadWriteLock at the same time?
no limit
Which of these scenario describes the best use case for using a ReadWriteLock?
Lots of threads need to both and modify the value of a shared variable.
Only a few threads need to both and modify the value of a shared variable.
Lots of threads need to read the value of a shared variable, but only a few thread need to modify its value. (답)
Lots of threads need to modify the value of a shared variable, but only a few thread need to read its value.
What happens when a thread calls Java's tryLock() method on a Lock that is NOT currently locked by another thread?
The method immediately returns true
What is the difference between the tryLock() and the regular lock() method in Java? 다시
tryLock() includes built-in error handling so you do not need a separate try/catch statement
tryLock() will continuously try to acquire the lock if it is already taken by another thread
tryLock() is a non-blocking version of the lock() method (답)
Why is the tryLock() method useful?
It enables a thread to execute alternate operations if the lock it needs to acquire is already taken. (답)
If multiple threads try to acquire a lock simultaneously, the tryLock() method will randomly pick one to succeed.
It enforces fairness among multiple threads competing for ownership of the same lock.
It includes built-in protection against common locking errors.
Which statement describes the relationship between Lock and ReentrantLock in Java?
ReentrantLock is a class that implements the Lock interface.
How many times must a thread unlock a ReentrantLock before another thread can acquire it?
as many times as that thread locked it
A ReentrantLock can be locked
_____. 다시once by multiple threads at the same time
multiple times by different threads
multiple times by the same thread (답)
Last updated