//2019/06/13 本周HT面试遇到的问题,答得不是很好,自己重新做一下。面试只需要写出线程间通信的方式,
//我当时大致知道思路,因为之前看过马士兵老师的多线程视频,但是代码写出来估计编译都是报错的。

//线程通信方式
public class ThreadTwo {

   //内部静态类,类去实现Runnable接口,obj通过构造方法,是希望这两个方法被一个参数锁住
public static class PrintABC implements Runnable{
Object o = null;

public PrintABC(Object o) {
this.o = o;
}

@Override
public void run() {
synchronized (o){
char ch = 'A';
for(int i=0;i<26;i++) {
            //ascii码吧
System.out.print((char) (ch + i));
            //之前这个写在了wait()方法后面,导致一直睡下去,无法唤醒了
o.notifyAll();
try {
o.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}

}
}
}
}

private static class Print123 implements Runnable{

Object o = null;

public Print123(Object o) {
this.o = o;
}

@Override
public void run() {
synchronized (o) {
for(int i=1;i<=52;i++) {
System.out.print(i);
if (i % 2 == 0) {
o.notifyAll();
try {
o.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}

}
}
}
}
}

public static void main(String[] args) {
     //同一把锁
Object o = new Object();
new Thread(new Print123(o)).start();
new Thread(new PrintABC(o)).start();
}

}

//互斥锁方式
public class ThreadTwoLock {

static class PrintAll{

Lock lock = new ReentrantLock();
Condition conChar = lock.newCondition();
Condition conNum = lock.newCondition();

boolean flag = true;

public void printABC(){
        //二话不说,方法一上来先锁上
lock.lock();

try {

for (int i = 0; i < 26; i++) {
            //每次打印之前判断自己还能不能打印,flag==true表示打印字母的要等下,让打印数字的来
if (flag) {
conChar.await();
}
char a = 'A';
System.out.print((char) (a + i));
            //打印了一个字母,让当前打印字母的线程停下,flag=true
flag=true;
            //唤醒打印数字的线程
conNum.signal();

}
} catch (InterruptedException e) {
e.printStackTrace();
} finally{
            //释放锁
lock.unlock();
}

}

public void print123(){

lock.lock();

try {

for (int i = 1; i <= 52; i++) {
if(!flag) {
conNum.await();
}
System.out.print(i);
if (i % 2 == 0) {
flag = false;
conChar.signal();

}
}

} catch (InterruptedException e) {
e.printStackTrace();
} finally {
lock.unlock();
}
}
}

public static void main(String[] args) {
final PrintAll pa = new PrintAll();
    //main方法里就负责创建和启动线程,别的啥也不做
new Thread(()->{
pa.printABC();
}).start();
new Thread(()->{
pa.print123();
}).start();

}
}

运行结果:
12A34B56C78D910E1112F1314G1516H1718I1920J2122K2324L2526M2728N2930O3132P3334Q3536R3738S3940T4142U4344V4546W4748X4950Y5152Z

最新文章

  1. 使用Flask设计带认证token的RESTful API接口[翻译]
  2. 细数iOS上的那些安全防护
  3. 1.3 第一个C#程序
  4. (转)as3效率优化
  5. MyBatis操作指南-搭建项目基础环境(基于Java API)含log4j2配置
  6. 【kd-tree】bzoj3053 The Closest M Points
  7. Windows Storage Server 2008 R2 Standard(64位)之ASM(Automated Storage Manager)管理
  8. mysql 求时间段平均值
  9. .net4.0注册到IIS
  10. IOS开发问题录:如何在Swift中引入Head文件?
  11. PAT-乙级-1043. 输出PATest(20)
  12. Javascript substr方法在某些浏览器下行为出现BUG的补丁代码
  13. 最小生成树问题(Kruskal 算法)(克鲁斯卡尔)
  14. (转)linux下fork的运行机制
  15. Hacker(14)----扫描目标计算机端口
  16. 超哥笔记 -- 用户管理、权限设置、进程管理、中文配置、计划任务和yum源配置(5)
  17. centos 7 一键安装gitlab
  18. 手动制作openstack windows镜像
  19. 关于SAN和NAS的区别-转
  20. python之demo2----改编自python官方提供的turtle_yinyang.py画阴阳的demo

热门文章

  1. excel 无效引用 所引用的单元格不能位于256列
  2. python 编写名字管理系统
  3. docker-搭建单机 kafka+zookeeper
  4. DockerFile系统的学习
  5. canal 整合RabbitMQ
  6. Hive Sql的窗口函数
  7. 一篇理解什么是CanSet, CanAddr?
  8. 查询时间段内所有日期(限foton)
  9. 史上最全的Kuberenetes 常用命令手册
  10. 【Luogu】P6232 [eJOI2019]挂架 题解