Java Concurrency
Basic Thread Synchronization
zxholy@gmail.com
In this chapter, we will cover:
● Synchronizing a method
● Arranging independent attributes in
synchronized classes
● Using conditions in synchronized code
● Synchronizing a block of code with a Lock
● Synchronizing data access with read/write
locks
● Modifying Lock fairness
● Using multiple conditions in a Lock
Introduction
● Critical section
A critical section is a block of code that
accesses a shared resource and can't be
executed by more than one thread at the same
time.
Introduction
● Synchronization mechanisms
When a thread wants access to a critical section, it uses
one of those synchronization mechanisms to find out if
there is any other thread executing the critical section.
If not, the thread enters the critical section.
Otherwise, the thread is suspended by the
synchronization mechanism until the thread that is
executing the critical section ends it.
When more than one thread is waiting for a thread to
finish the execution of a critical section, the JVM chooses
one of them, and the rest wait for their turn.
Introduction
Two basic synchronization mechanisms:
● The keyword synchronized
● The Lock interface and its implementations
Synchronizing a method
Every method declared with the
synchronized keyword is a critical section
and Java only allows the execution of one of
the critical sections of an object.
Static methods have a different behavior. Two
threads can access two different
synchronized methods if one is static and
the other one is not.
We will have a bank account and two threads;
one that transfers money to the account and
another one that withdraws money from the
account.
Synchronization mechanisms ensures that
the final balance of the account will be correct.
How to do it…
Create a class called: Account
One attribute: private double amount;
Two method:
addAmount() substractAmount();
Two class: Bank and Company
How it works...
When remove synchronized keyword.
The order of execution of the threads is not
guaranteed by the JVM.
Using the synchronized keyword, we
guarantee correct access to shared data in
concurrent applications.
There is more...
The synchronized keyword penalizes the
performance of the application, so you must
only use it on methods that modify shared data
in a concurrent environment.
You can use recursive calls with
synchronized methods.
We can use the synchronized keyword to
protect the access to a block of code instead of
an entire method.
Arranging independent attributes in
synchronized classes
When executing the synchronized method
which you use the this keyword as a
parameter, you can only use other object
references.
But, now...
● Two independent attributes, synchronize the
access to each variable.
● One thread accessing one attribute, another
thread accessing another one.
Simulates a cinema with two screens and two
ticket offices.
When a ticket office sells tickets, they are for
one of the two cinemas, but not for both.
So the numbers of free seats in each cinema
are independent attributes.
How to do it...
Cinema class:
Two methods:
Two ticket-office:
How it works...
When you use an object as a parameter of
synchronized method, JVM guarantees that:
Only one thread can have access to all the
blocks of code protected with that object.
Note: objects, not classes.
We have two objects that controls access to the
vacanciesCinema1 attribute and
vacanciesCinema2 attribute separately.
One thread can modify one attribute each time.
Using conditions in synchronized
code
Producer-consumer problem:
A classic problem in concurrent programming.
● A data buffer
○ A shared data structure
● One or more producers
○ Can’t save data in the buffer if it’s full
● One or more consumers
○ Can’t take data from the buffer if it’s empty
Java provides the wait(), notify() and
notifyAll() method s implemented in the
Object class.
wait() method
Called by a thread, inside a synchronized
block of code (Outside, JVM throws an
IllegalMonitorStateException
exception).
The JVM puts the thread to sleep and releases
the resources.
To wake up the thread, you must call the
notify() or notifyAll() method inside a
block of code protected by the same object.
Implement the producer-consumer problem
using the synchronized keyword and the
wait(), notify(), and notifyAll()
methods.
How to do it...
EventStorage class:
set() method:
get() method:
Producer and Consumer class:
Main class:
How it works...
Synchronizing a block of code with a
Lock
Another mechanism for the synchronization of
blocks of code.
Based on Lock interface and classes that
implement it (as ReentrantLock).
Compare Lock and synchronized
● The mechanism based on Lock interface is
more flexible.
● The Lock interfaces provide additional
functionalities, as tryLock().
● Allow a separation of read and write
operations having multiple readers and only
one modifier.
● Better performance
Using the Lock interface and the
ReentrantLock class that implements it,
implementing a program that simulates a print
queue.
How to do it...
How it works...
There’s more...
tryLock() method returns a boolean value,
true if the thread gets the control of the lock,
and false if not.
The ReentrantLock class also allows the use
of recursive calls.
Avoid deadlocks.
Situation: Two or more threads are blocked
waiting for locks that never will be unlocked.
Reason: Both threads try to get the locks in the
opposite order.
Modifying Lock fairness
The constructor of the ReentrantLock and
ReentrantReadWriteLock classes admits a
boolean parameter named fair:
false: non-fair mode
selects one without any criteria.
true: fair mode
How to do it...
Job class
main() method:
How it works...
fair: true
fair: false
fair: false
Synchronizing data access with
read/write locks
One of the most significant improvements
offered by locks is the ReadWriteLock
interface and the ReentrantReadWriteLock
class, the unique one that implements it.
Two locks: read/write
Use ReadWriteLock to control the access to
an object that stores the prices of two products.
How to do it...
PricesInfo class:
getPrice1() setPrice()
Reader class:
Writer class:
main() method:
How it works...
Ensure the correct use of these locks, using
them with the same purposes.
When you get the read lock of a Lock
interface, you can’t modify the calue of the
variable.
Using multiple conditions in a Lock
A lock may be associated with one or more
conditions. These conditions are declared in
the Condition interface.
The Condition interface provides the
mechanisms to suspend a thread and to wake
up a suspended thread.
Condition
● Synchronized + monitor methods(wait,
notify and notifyAll)
● Lock + Condition
To obtain a Condition instance for a
particular Lock instance use its
newCondition() method.
Producer-consumer problem.
We have a data buffer, one or more producers
of data that save it in the buffer, and one or
more consumers of data that take it from the
buffer as explained earlier in this chapter
How to do it...
How it works...
When a thread calls the await() method of a
condition, it automatically frees the control of
the lock, so that another thread can get it and
begin the execution of the same, or another
critical section protected by that lock.
You must be careful with the use of await()
and signal().
You can use conditions with the ReadLock and
WriteLock locks of a read/write lock.
End
Thank you!

[Java concurrency]02.basic thread synchronization

  • 1.
    Java Concurrency Basic ThreadSynchronization zxholy@gmail.com
  • 2.
    In this chapter,we will cover: ● Synchronizing a method ● Arranging independent attributes in synchronized classes ● Using conditions in synchronized code ● Synchronizing a block of code with a Lock ● Synchronizing data access with read/write locks ● Modifying Lock fairness ● Using multiple conditions in a Lock
  • 3.
    Introduction ● Critical section Acritical section is a block of code that accesses a shared resource and can't be executed by more than one thread at the same time.
  • 4.
    Introduction ● Synchronization mechanisms Whena thread wants access to a critical section, it uses one of those synchronization mechanisms to find out if there is any other thread executing the critical section. If not, the thread enters the critical section. Otherwise, the thread is suspended by the synchronization mechanism until the thread that is executing the critical section ends it. When more than one thread is waiting for a thread to finish the execution of a critical section, the JVM chooses one of them, and the rest wait for their turn.
  • 5.
    Introduction Two basic synchronizationmechanisms: ● The keyword synchronized ● The Lock interface and its implementations
  • 6.
    Synchronizing a method Everymethod declared with the synchronized keyword is a critical section and Java only allows the execution of one of the critical sections of an object. Static methods have a different behavior. Two threads can access two different synchronized methods if one is static and the other one is not.
  • 7.
    We will havea bank account and two threads; one that transfers money to the account and another one that withdraws money from the account. Synchronization mechanisms ensures that the final balance of the account will be correct.
  • 8.
    How to doit… Create a class called: Account One attribute: private double amount; Two method: addAmount() substractAmount();
  • 9.
    Two class: Bankand Company
  • 11.
    How it works... Whenremove synchronized keyword.
  • 12.
    The order ofexecution of the threads is not guaranteed by the JVM. Using the synchronized keyword, we guarantee correct access to shared data in concurrent applications.
  • 13.
    There is more... Thesynchronized keyword penalizes the performance of the application, so you must only use it on methods that modify shared data in a concurrent environment. You can use recursive calls with synchronized methods.
  • 14.
    We can usethe synchronized keyword to protect the access to a block of code instead of an entire method.
  • 15.
    Arranging independent attributesin synchronized classes When executing the synchronized method which you use the this keyword as a parameter, you can only use other object references. But, now... ● Two independent attributes, synchronize the access to each variable. ● One thread accessing one attribute, another thread accessing another one.
  • 16.
    Simulates a cinemawith two screens and two ticket offices. When a ticket office sells tickets, they are for one of the two cinemas, but not for both. So the numbers of free seats in each cinema are independent attributes.
  • 17.
    How to doit... Cinema class:
  • 18.
  • 19.
  • 21.
    How it works... Whenyou use an object as a parameter of synchronized method, JVM guarantees that: Only one thread can have access to all the blocks of code protected with that object. Note: objects, not classes.
  • 22.
    We have twoobjects that controls access to the vacanciesCinema1 attribute and vacanciesCinema2 attribute separately. One thread can modify one attribute each time.
  • 23.
    Using conditions insynchronized code Producer-consumer problem: A classic problem in concurrent programming. ● A data buffer ○ A shared data structure ● One or more producers ○ Can’t save data in the buffer if it’s full ● One or more consumers ○ Can’t take data from the buffer if it’s empty
  • 24.
    Java provides thewait(), notify() and notifyAll() method s implemented in the Object class.
  • 25.
    wait() method Called bya thread, inside a synchronized block of code (Outside, JVM throws an IllegalMonitorStateException exception). The JVM puts the thread to sleep and releases the resources.
  • 26.
    To wake upthe thread, you must call the notify() or notifyAll() method inside a block of code protected by the same object.
  • 27.
    Implement the producer-consumerproblem using the synchronized keyword and the wait(), notify(), and notifyAll() methods.
  • 28.
    How to doit... EventStorage class:
  • 29.
  • 30.
  • 31.
  • 32.
  • 33.
  • 35.
    Synchronizing a blockof code with a Lock Another mechanism for the synchronization of blocks of code. Based on Lock interface and classes that implement it (as ReentrantLock).
  • 36.
    Compare Lock andsynchronized ● The mechanism based on Lock interface is more flexible. ● The Lock interfaces provide additional functionalities, as tryLock(). ● Allow a separation of read and write operations having multiple readers and only one modifier. ● Better performance
  • 37.
    Using the Lockinterface and the ReentrantLock class that implements it, implementing a program that simulates a print queue.
  • 38.
    How to doit...
  • 41.
  • 42.
    There’s more... tryLock() methodreturns a boolean value, true if the thread gets the control of the lock, and false if not.
  • 43.
    The ReentrantLock classalso allows the use of recursive calls. Avoid deadlocks. Situation: Two or more threads are blocked waiting for locks that never will be unlocked. Reason: Both threads try to get the locks in the opposite order.
  • 44.
    Modifying Lock fairness Theconstructor of the ReentrantLock and ReentrantReadWriteLock classes admits a boolean parameter named fair: false: non-fair mode selects one without any criteria. true: fair mode
  • 45.
    How to doit... Job class
  • 47.
  • 48.
  • 49.
  • 50.
  • 51.
    Synchronizing data accesswith read/write locks One of the most significant improvements offered by locks is the ReadWriteLock interface and the ReentrantReadWriteLock class, the unique one that implements it. Two locks: read/write
  • 52.
    Use ReadWriteLock tocontrol the access to an object that stores the prices of two products.
  • 53.
    How to doit... PricesInfo class:
  • 54.
  • 55.
  • 56.
  • 57.
  • 58.
  • 59.
    Ensure the correctuse of these locks, using them with the same purposes. When you get the read lock of a Lock interface, you can’t modify the calue of the variable.
  • 60.
    Using multiple conditionsin a Lock A lock may be associated with one or more conditions. These conditions are declared in the Condition interface. The Condition interface provides the mechanisms to suspend a thread and to wake up a suspended thread.
  • 61.
    Condition ● Synchronized +monitor methods(wait, notify and notifyAll) ● Lock + Condition To obtain a Condition instance for a particular Lock instance use its newCondition() method.
  • 62.
    Producer-consumer problem. We havea data buffer, one or more producers of data that save it in the buffer, and one or more consumers of data that take it from the buffer as explained earlier in this chapter
  • 63.
    How to doit...
  • 72.
    How it works... Whena thread calls the await() method of a condition, it automatically frees the control of the lock, so that another thread can get it and begin the execution of the same, or another critical section protected by that lock.
  • 73.
    You must becareful with the use of await() and signal(). You can use conditions with the ReadLock and WriteLock locks of a read/write lock.
  • 74.