I am trying to understand the concept of ReadWriteLock
and implemented the below simple example. From what I have understood, whenever a thread has a readlock
, another thread can acquire the readlock
. But for a thread with writelock
, no other thread can acquire the write/read lock
, until the other thread releases the lock. However from the output of the below program, I noticed that before the WriterOdd
release the lock(prints the output of releasing the lock), the Reader
threads come in and reads the number
String. Is it because just after releasing the writelock
the reader
threads come in and then the print statement of releasing the writelock
is printed?
public static void main(String[] args) {
new Thread(new Reader(), "Reader 1").start();
new Thread(new Reader(), "Reader 2").start();
new Thread(new WriterEven(), "Writer Even").start();
new Thread(new WriterOdd(), "Writer Odd").start();
}
public static class Reader implements Runnable {
public void run() {
for (int i = 1; i <= 6; i++) {
rwl.readLock().lock();
// rl.lock();
System.out.println(Thread.currentThread().getName() + " is reading" + number);
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
rwl.readLock().unlock();
}
}
}
}
public static class WriterEven implements Runnable {
public void run() {
System.out.println(Thread.currentThread().getName() + " is trying writing");
rwl.writeLock().lock();
System.out.println(Thread.currentThread().getName() + " got the lock");
for (int i = 2; i <= 6; i += 2) {
System.out.println(Thread.currentThread().getName() + " is writing");
number = number.concat(" " + i);
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
}
}
rwl.writeLock().unlock();
System.out.println(Thread.currentThread().getName() + " left the lock");
}
}
public static class WriterOdd implements Runnable {
public void run() {
System.out.println(Thread.currentThread().getName() + " is trying writing");
rwl.writeLock().lock();
System.out.println(Thread.currentThread().getName() + " got the lock");
for (int i = 1; i <= 5; i += 2) {
System.out.println(Thread.currentThread().getName() + " is writing");
number = number.concat(" " + i);
try {
Thread.sleep(2000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
}
}
rwl.writeLock().unlock();
System.out.println(Thread.currentThread().getName() + " left the lock");
}
}
OUTPUT:
Reader 2 is reading0
Reader 1 is reading0
Writer Even is trying writing
Writer Odd is trying writing
Writer Even got the lock
Writer Even is writing
Writer Even is writing
Writer Even is writing
Writer Odd got the lock
Writer Odd is writing
Writer Even left the lock
Writer Odd is writing
Writer Odd is writing
Reader 1 is reading0 2 4 6 1 3 5
Reader 2 is reading0 2 4 6 1 3 5
Writer Odd left the lock
Line of code that writes console message about releasing write lock is AFTER releasing the lock.
rwl.writeLock().unlock();
// here readers can read already
// because they are free to aquire lock
System.out.println(Thread.currentThread().getName() + " left the lock");