1、使用Lock
public class PrintABCUsingLock {
private int times;
private int state;
private Lock lock = new ReentrantLock ( ) ;
public PrintABCUsingLock ( int times) {
this . times = times;
}
public static void main ( String[ ] args) {
PrintABCUsingLock printABCUsingLock = new PrintABCUsingLock ( 10 ) ;
new Thread ( ( ) - > {
printABCUsingLock. printA ( ) ;
} ) . start ( ) ;
new Thread ( ( ) - > {
printABCUsingLock. printB ( ) ;
} ) . start ( ) ;
new Thread ( ( ) - > {
printABCUsingLock. printC ( ) ;
} ) . start ( ) ;
}
public void printA ( ) {
print ( "A" , 0 ) ;
}
public void printB ( ) {
print ( "B" , 1 ) ;
}
public void printC ( ) {
print ( "C" , 2 ) ;
}
private void print ( String name, int targetState) {
for ( int i = 0 ; i < times; ) {
lock. lock ( ) ;
if ( state % 3 == targetState) {
state++ ;
i++ ;
System. out. print ( name) ;
}
lock. unlock ( ) ;
}
}
}
2、使用Semaphore
public class PrintABCUsingSemaphore {
private int times;
Semaphore semaphoreA = new Semaphore ( 1 ) ;
Semaphore semaphoreB = new Semaphore ( 0 ) ;
Semaphore semaphoreC = new Semaphore ( 0 ) ;
public PrintABCUsingSemaphore ( int times) {
this . times = times;
}
public void printA ( ) {
try {
print ( "A" , semaphoreA, semaphoreB) ;
} catch ( InterruptedException e) {
e. printStackTrace ( ) ;
}
}
public void printB ( ) {
try {
print ( "B" , semaphoreB, semaphoreC) ;
} catch ( InterruptedException e) {
e. printStackTrace ( ) ;
}
}
public void printC ( ) {
try {
print ( "C" , semaphoreC, semaphoreA) ;
} catch ( InterruptedException e) {
e. printStackTrace ( ) ;
}
}
public void print ( String str, Semaphore current, Semaphore next) throws InterruptedException {
for ( int i = 0 ; i < times; ++ i) {
current. acquire ( ) ;
System. out. print ( str) ;
next. release ( ) ;
}
}
public static void main ( String[ ] args) {
PrintABCUsingSemaphore printABCUsingSemaphore = new PrintABCUsingSemaphore ( 10 ) ;
new Thread ( ( ) - > {
printABCUsingSemaphore. printA ( ) ;
} ) . start ( ) ;
new Thread ( ( ) - > {
printABCUsingSemaphore. printB ( ) ;
} ) . start ( ) ;
new Thread ( ( ) - > {
printABCUsingSemaphore. printC ( ) ;
} ) . start ( ) ;
}
}
3、使用wait/notify
public class PrintABCUsingWaitNotify {
private int times;
private int state;
private Object objectA = new Object ( ) ;
private Object objectB = new Object ( ) ;
private Object objectC = new Object ( ) ;
public PrintABCUsingWaitNotify ( int times) {
this . times = times;
}
public static void main ( String[ ] args) {
PrintABCUsingWaitNotify printABCUsingWaitNotify = new PrintABCUsingWaitNotify ( 10 ) ;
new Thread ( ( ) - > {
printABCUsingWaitNotify. printA ( ) ;
} ) . start ( ) ;
new Thread ( ( ) - > {
printABCUsingWaitNotify. printB ( ) ;
} ) . start ( ) ;
new Thread ( ( ) - > {
printABCUsingWaitNotify. printC ( ) ;
} ) . start ( ) ;
}
public void printA ( ) {
try {
print ( "A" , 0 , objectA, objectB) ;
} catch ( InterruptedException e) {
e. printStackTrace ( ) ;
}
}
public void printB ( ) {
try {
print ( "B" , 1 , objectB, objectC) ;
} catch ( InterruptedException e) {
e. printStackTrace ( ) ;
}
}
public void printC ( ) {
try {
print ( "C" , 2 , objectC, objectA) ;
} catch ( InterruptedException e) {
e. printStackTrace ( ) ;
}
}
private void print ( String name, int targetState, Object current, Object next) throws InterruptedException {
for ( int i = 0 ; i < times; ) {
synchronized ( current) {
while ( state % 3 != targetState) {
current. wait ( ) ;
}
state++ ;
i++ ;
System. out. print ( name) ;
synchronized ( next) {
next. notify ( ) ;
}
}
}
}
}
4、使用Lock/Condition
public class PrintABCUsingLockCondition {
private int times;
private int state;
private Lock lock = new ReentrantLock ( ) ;
private Condition conditionA = lock. newCondition ( ) ;
private Condition conditionB = lock. newCondition ( ) ;
private Condition conditionC = lock. newCondition ( ) ;
public PrintABCUsingLockCondition ( int times) {
this . times = times;
}
public static void main ( String[ ] args) {
PrintABCUsingLockCondition printABCUsingLockCondition = new PrintABCUsingLockCondition ( 10 ) ;
new Thread ( ( ) - > {
printABCUsingLockCondition. printA ( ) ;
} ) . start ( ) ;
new Thread ( ( ) - > {
printABCUsingLockCondition. printB ( ) ;
} ) . start ( ) ;
new Thread ( ( ) - > {
printABCUsingLockCondition. printC ( ) ;
} ) . start ( ) ;
}
public void printA ( ) {
print ( "A" , 0 , conditionA, conditionB) ;
}
public void printB ( ) {
print ( "B" , 1 , conditionB, conditionC) ;
}
public void printC ( ) {
print ( "C" , 2 , conditionC, conditionA) ;
}
private void print ( String name, int targetState, Condition current, Condition next) {
for ( int i = 0 ; i < times; ) {
lock. lock ( ) ;
try {
while ( state % 3 != targetState) {
current. await ( ) ;
}
state++ ;
i++ ;
System. out. print ( name) ;
next. signal ( ) ;
} catch ( InterruptedException e) {
e. printStackTrace ( ) ;
} finally {
lock. unlock ( ) ;
}
}
}
}