悲观锁、乐观锁
悲观锁:一上来就加锁,没有安全感,每次只能一个线程进入访问完毕后,再解锁。线程安全,性能较差。
乐观锁:一开始不上锁,认为是没有问题的,等要出现线程安全问题的时候才开始控制。线程安全,性能较好
练习
需求:
- 有100份礼品,小明、小红同时发送,当剩下的礼品小于10的时候则不再送出利用多线程模拟该过程并将线程的名称打印出来,并最后在控制台分别打印小红、小明各种送出多少份礼品
Test类
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
public class Test {
public static void main(String[] args) throws Exception {
// 目标:有100份礼品,小明、小红同时发送,当剩下的礼品小于10的时候则不再送出
// 利用多线程模拟该过程并将线程的名称打印出来,并最后在控制台分别打印小红、小明各种送出多少份礼品
// 拿100分礼品到程序中来
List<String> gift = new ArrayList<>();
String[] names = {"口红","包包","鲜花","剃须刀","皮带","手表"};
Random r = new Random();
for (int i = 0; i < 100; i++) {
gift.add(names[r.nextInt(names.length)] + (i+1));
}
System.out.println(gift);
//定义线程类,创建线程对象,去集合中拿礼物给别人
SendThread xm = new SendThread(gift,"小明");
xm.start();
SendThread xh = new SendThread(gift,"小红");
xh.start();
xm.join();
xh.join();
System.out.println(xm.getCount());
System.out.println(xh.getCount());
}
}
SendThread类
import java.util.List;
import java.util.Random;
public class SendThread extends Thread{
private List<String> gift;
private int count;
public SendThread(List<String> gift, String name) {
super(name);
this.gift = gift;
}
@Override
public void run() {
String name = Thread.currentThread().getName();
// 小明、小红发礼物出去
// 实现线程安全问题
// 注意1:锁必须唯一
Random r = new Random();
while (true){
synchronized (gift){
if (gift.size() < 10){
break;
}
String rs = gift.remove(r.nextInt(gift.size()));
System.out.println(name + "发出了:" + rs);
count++;
}
}
}
public int getCount() {
return count;
}
public void setCount(int count){
this.count = count;
}
}