/** * (1)在 main方法中启动两个线程 * (2)第 1个线程循环随机打印 100以内的整数 * (3)直到第 2个线程从键盘读取了 “Q”命令。 */public class Homework01 { public static void main(String[] args) { A a = new A(); B b = new B(a); a.start(); b.start(); } } //创建A线程类 class A extends Thread{ private boolean loop = true; @Override public void run() { //循环随机打印 100以内的整数 while (loop){ System.out.println((int)(Math.random() * 100 + 1)); try { Thread.sleep(1000); //休眠一秒 } catch (InterruptedException e) { throw new RuntimeException(e); } } System.out.println("a线程退出"); } public void setLoop(boolean loop) { //修改loop变量 this.loop = loop; } } //直到第 2个线程从键盘读取了 “Q”命令。 class B extends Thread{ private A a; private Scanner scanner = new Scanner(System.in); public B(A a) {//构造器中,直接传入A类对象 this.a = a; } @Override public void run() { while (true) { //接收用户输入 System.out.println("请输入指令(Q)表示退出"); char key = scanner.next().toUpperCase().charAt(0); if (key == 'Q') { //已通知方式结束a线程 a.setLoop(false); System.out.println("b线程退出"); break;//b线程退出 } } } }
输出:
请输入指令(Q)表示退出
53
44
20
q
b线程退出
a线程退出
/** * (1)有 2个用户分别从同一个卡上取钱(总额:10000) * (2)每次都取 1000,当余额不足时,就不能取款了 * (3)不能出现超取现象 => 线程同步问题. */public class Homework02 { public static void main(String[] args) { Th th = new Th(); new Thread(th).start(); new Thread(th).start(); } } //因为这里涉及到多个线程共享资源,所以我们实现Runnable接口方式 class Th implements Runnable{ private int money = 10000; @Override public void run() { while (true) { //1、这里使用synchronized 实现了线程同步 //2、当多个线程执行到这里时,就会去争夺 this对象锁 //3、哪个线程争夺到(获取)this对象锁,就执行synchronized 代码块,执行完后,会释放this对象锁 //4、争夺不到this对象锁,就blocked ,准备继续争夺 //5、this对象锁是非公平锁. synchronized (this) { if (money < 1000) { System.out.println("余额不足"); break; } money -= 1000; System.out.println(Thread.currentThread().getName() + "取出1000,当前余额:" + money); } } } }
输出:
Thread-0取出1000,当前余额:9000
Thread-0取出1000,当前余额:8000
Thread-1取出1000,当前余额:7000
Thread-1取出1000,当前余额:6000
Thread-1取出1000,当前余额:5000
Thread-1取出1000,当前余额:4000
Thread-1取出1000,当前余额:3000
Thread-1取出1000,当前余额:2000
Thread-1取出1000,当前余额:1000
Thread-1取出1000,当前余额:0
余额不足
余额不足