美文网首页Android开发Android开发经验谈
腾讯面试Android高级岗,居然被一个多线程基础面倒了?

腾讯面试Android高级岗,居然被一个多线程基础面倒了?

作者: Androidgiao | 来源:发表于2019-10-10 17:00 被阅读0次

    前言

    一个在深圳从事开发五年的老友一个月前从原公司辞职后,昨天去腾讯总部面试Android高级岗,一面的时候,自我介绍后,陆陆续续问了很多问题,有着五年的从业经验很多项目开发的技术问题都回答的很通顺,面试官也很满意,就在最后以为自己要顺利通过时,【多线程——进程线程】,一个基础问题一时没有答上来就失去了二面的机会!

    image

    在我的身边不止发生了这一个大厂面试被拒的例子,所以从他们的身上我有总结出一个特点,无论是大厂BAT之类还是中厂,在面试过程中是逃不掉各类的开发基础问题,很多不注意的小细节正是打败我们的关键!走出自己的技术圈子,基础是必不可少的。

    下面我分享一下我在TX官方群里收集的多线程面试专题,(更多大厂面试专题含答案文末一起分享)

    1.什么是线程

    线程就是进程中运行的多个子任务,是操作系统调用的最小单元

    2.线程的状态

    New:新建状态,new出来,还没有调用start
    Runnable:可运行状态,调用start进入可运行状态,可能运行也可能没有运行,取决于操作系统的调度
    Blocked:阻塞状态,被锁阻塞,暂时不活动,阻塞状态是线程阻塞在进入synchronized关键字修饰的方法或代码块(获取锁)时的状态。
    Waiting:等待状态,不活动,不运行任何代码,等待线程调度器调度,wait sleep
    Timed Waiting:超时等待,在指定时间自行返回
    Terminated:终止状态,包括正常终止和异常终止

    3.线程的创建

    a.继承Thread重写run方法
    b.实现Runnable重写run方法
    c.实现Callable重写call方法
    实现Callable和实现Runnable类似,但是功能更强大,具体表现在
    a.可以在任务结束后提供一个返回值,Runnable不行
    b.call方法可以抛出异常,Runnable的run方法不行
    c.可以通过运行Callable得到的Fulture对象监听目标线程调用call方法的结果,得到返回值,(fulture.get(),调用后会阻塞,直到获取到返回值)

    4.线程中断

    一般情况下,线程不执行完任务不会退出,但是在有些场景下,我们需要手动控制线程中断结束任务,Java中有提供线程中断机制相关的Api,每个线程都一个状态位用于标识当前线程对象是否是中断状态

    public boolean isInterrupted() //判断中断标识位是否是true,不会改变标识位public void interrupt() //将中断标识位设置为truepublic static boolean interrupted() //判断当前线程是否被中断,并且该方法调用结束的时候会清空中断标识位

    需要注意的是interrupt()方法并不会真的中断线程,它只是将中断标识位设置为true,具体是否要中断由程序来判断,如下,只要线程中断标识位为false,也就是没有中断就一直执行线程方法

    new Thread(new Runnable(){
    while(!Thread.currentThread().isInterrupted()){
    //执行线程方法
    }
    }).start();
    前边我们提到了线程的六种状态,New Runnable Blocked Waiting Timed Waiting Terminated,那么在这六种状态下调用线程中断的代码会怎样呢,New和Terminated状态下,线程不会理会线程中断的请求,既不会设置标记位,在Runnable和Blocked状态下调用interrupt会将标志位设置位true,在Waiting和Timed Waiting状态下会发生InterruptedException异常,针对这个异常我们如何处理?
    1.在catch语句中通过interrupt设置中断状态,因为发生中断异常时,中断标志位会被复位,我们需要重新将中断标志位设置为true,这样外界可以通过这个状态判断是否需要中断线程
    try{
    ....
    }catch(InterruptedException e){
    Thread.currentThread().interrupt();
    }
    2.更好的做法是,不捕获异常,直接抛出给调用者处理,这样更灵活

    5.Thread为什么不能用stop方法停止线程

    从SUN的官方文档可以得知,调用Thread.stop()方法是不安全的,这是因为当调用Thread.stop()方法时,会发生下面两件事:
    1.即刻抛出ThreadDeath异常,在线程的run()方法内,任何一点都有可能抛出ThreadDeath Error,包括在catch或finally语句中。
    2.释放该线程所持有的所有的锁。调用thread.stop()后导致了该线程所持有的所有锁的突然释放,那么被保护数据就有可能呈现不一致性,其他线程在使用这些被破坏的数据时,有可能导致一些很奇怪的应用程序错误。

    6.重入锁与条件对象,同步方法和同步代码块

    7.volatile关键字

    8.java内存模型

    9.原子性 可见性 有序性

    10.线程池ThreadPoolExecutor

    11.线程池的种类

    12.线程同步机制与原理,举例说明

    13.arrayList与linkedList的读写时间复杂度

    14.为什么HashMap线程不安全(hash碰撞与扩容导致)

    15.进程线程的区别

    16.Binder的内存拷贝过程

    17.传统IPC机制的通信原理(2次内存拷贝)

    18.Java内存模型(记住堆栈是内存分区,不是模型)

    19.类的加载过程

    20.什么情况下会触发类的初始化

    21.双亲委托模式

    22.双亲委托模式的好处

    23.死锁的产生条件,如何避免死锁

    24.App启动流程

    25.Android单线程模型

    26.RecyclerView在很多方面能取代ListView,Google为什么没把ListView划上一条过时的横线?

    27.HashMap如何保证元素均匀分布

    image

    答案的篇幅过长,文中放进去不方便大家的阅读,还是以文档的形式看比较便于查看学习,有需要的朋友可以去加入那个腾讯的官方群,简信我回复【资料】,里面不仅仅有Android各类专题面试资料,BAT高级源码面试题,还有提供学习的系统进阶视频资料,现在面对找工作的困境,需要提升自己的朋友们推荐加入。

    最后

    大家所认知的,给程序员定义的标签一定少不了“宅”这个字,那么 这个宅字我个人所理解的有两层意思,第一就是像很多人所想象的爱宅在家和编程代码过一辈子,第二种呢,就是盲目宅在自己的技术舒适区,眼界不宽,不能看到别人的长处,吸收别人的优点。虽然我不能得知这个宅字是不是真的能运用到所有人身上,但针对我这个老友,他,就是这样。

    相关文章

      网友评论

        本文标题:腾讯面试Android高级岗,居然被一个多线程基础面倒了?

        本文链接:https://www.haomeiwen.com/subject/seeapctx.html