你真得會寫java多線程手撕代碼題嗎?
多線程部分是java中最重要的一部分之一,所以也是面試官經常問的部分。
頭條面試的時候,經常會讓你手撕一些多線程代碼題。下面介紹幾個經典
得面試題
兩個線程,線程1打印A,線程2打印B,兩個線程同時併發,要求保證先打印A,後打印B
使用synchronized
+ wait、notify
public class Main{
static class Number{
public int num = 1;
Number(){}
}
public static Number number = new Number();
public static void main(String []args) {
Thread a = new Thread(new Runnable(){
@Override
public void run() {
synchronized(number){
try{
//避免假喚醒
while(number.num == 2) number.wait();
}catch(Exception e) {
e.printStackTrace();
}
System.out.println("A");
number.num = 2;
number.notify();
}
}
});
Thread b = new Thread(new Runnable(){
@Override
public void run() {
synchronized(number) {
try{
while(number.num == 1) number.wait();
}catch(Exception e){
e.printStackTrace();
}
System.out.println("B");
number.num = 1;
number.notify();
}
}
});
b.start();
try{
Thread.sleep(1000);
}catch(Exception e) {
e.printStackTrace();
}
a.start();
}
}
使用ReetrantLock+Condition
import java.util.concurrent.locks.*;
public class Main{
public static ReentrantLock lock = new ReentrantLock();
public static Condition condition = lock.newCondition();
public static int num = 1;
public static void main(String []args) {
Thread a = new Thread(new Runnable(){
@Override
public void run() {
lock.lock();
try{
while(num == 2) condition.await();
}catch(Exception e) {
e.printStackTrace();
}
System.out.println("A");
num = 2;
condition.signal();
lock.unlock();
}
});
Thread b = new Thread(new Runnable(){
@Override
public void run() {
lock.lock();
try{
while(num == 1) condition.await();
}catch(Exception e) {
e.printStackTrace();
}
System.out.println("B");
num = 1;
condition.signal();
lock.unlock();
}
});
b.start();
try{
Thread.sleep(1000);
}catch(Exception e){
e.printStackTrace();
};
a.start();
}
}
兩個線程,一個線程打印奇數,一個線程打印偶數,控制先一個奇數後一個偶數這種順序.使用ReetrantLock+Condition
import java.util.concurrent.locks.*;
public class Main{
public static ReentrantLock lock = new ReentrantLock();
public static Condition condition = lock.newCondition();
public static int num = 2;
public static void main(String []args) {
Thread a = new Thread(new Runnable(){
@Override
public void run() {
try{
for(int i = 2; i <= 10; i=i+2) {
lock.lock();
while(num == 2) condition.await();
System.out.print(i);
num = 2; condition.signal();
lock.unlock();
}
}catch(Exception e) {
e.printStackTrace();
}
}
});
Thread b = new Thread(new Runnable(){
@Override
public void run() {
try{
for(int i = 1; i <= 10; i = i+2){
lock.lock();
while(num == 1) condition.await();
System.out.print(i);
num = 1; condition.signal();
lock.unlock();
}
}catch(Exception e) {
e.printStackTrace();
}
}
});
a.start();
try{
Thread.sleep(10);
}catch(Exception e){
e.printStackTrace();
};
b.start();
}
}