zoukankan      html  css  js  c++  java
  • 面试:Semaphore(信号量)的成长之路

    2019最寒冷,面试跳槽不能等

    马上就3月份了,所谓的金三银四招聘季。2019年也许是互联网最冷清的一年,很多知名的大型互联网公司都裁员过冬。当然也有一些公司还在持续招人的,比如阿里就宣称不裁员,反而要增加更多的就业机会。

    面试大公司的职位,基础显得很重要,在并发编程这块问的自然也比较多。对于一个Java程序员而言,能否熟练掌握并发编程是判断他优秀与否的重要标准之一。因为并发编程是Java语言中最为晦涩的知识点,它涉及操作系统、内存、CPU、编程语言等多方面的基础能力,更为考验一个程序员的内功。

    今天我们就来聊聊Java中的Semaphore(信号量)在面试过程中会有哪些问题,以及如何回答。

    问题一:什么是信号量?

    信号量就相当于一个计数器,通常用来限制线程的数量。每个线程操作前会先获取一个许可证,逻辑处理完成之后就归还这个许可证。

    就好比我们去网吧上网,信号量初始化的大小就好比网吧中所有的电脑。当有人交费开机之后,可用电脑的数量就少了1台。依次类推,当有人下机之后可用的电脑数量又多了。当机器被用完之后新来的客人就只能等待前面的人下机,这就是归还许可证。

    问题二:信号量的应用场景?

    信号量的核心功能就是用来对资源做一定的限制,防止出现崩塌现象。最适用的应用场景那就是限流,通过限流来保护对应的资源。

    在Spring Cloud中我们会用Hystrix来保护服务,进行熔断降级。在Hystrix中有两种模式,分别是线程池和信号量,说到这里大家明白了吧,信号量的作用。

    在限流层面,最简单的实现可以用信号量来实现本地限流操作,集群限流必须得依赖第三方中间件,比如Redis。

    问题三:你有在项目中使用过信号量吗?

    这个问题那就得根据你的实际情况来说明了,如果确实没用用过,你可以稍微构思一下,在哪些业务场景下可以使用,然后封装下,对吧,搞Java的怎么能不会封装呢,然后侃侃而谈,我用过啊,我在那个啥....用过啊....为了满足xxx的需求啊。。。

    比如:在我们的爬虫系统中,都会通过多线程的方式去爬取数据,而有些小型网站,并发能力不是特别强,线程数一上去就很慢,然后服务出现504,502最后爬取不了,这个时候就需要对并发抓取量做一些限制了,这个时候就可以用信号量来进行限制。

    还有些并发量强的网站,能抗住很多的请求,但是人家的反爬取策略做的好啊,请求数量稍微多一点就能识别你是机器,给你封了,这也是需要做一些限制。

    剩下的就靠你自己吹牛啦。。。

    public class SemaphoreDemo {
    	public static void main(String[] args) {
    		ExecutorService executorService = Executors.newFixedThreadPool(10);
    		Semaphore semaphore = new Semaphore(2);
    		for (;;) {
    			executorService.execute(() -> {
    				try {
    					semaphore.acquire();
    					System.out.println("抓取数据逻辑");
    				} catch (Exception e) {
    					e.printStackTrace();
    				} finally {
    					semaphore.release();
    				}
     			});
    		}
    	}
    }
    

    总结推荐

    我这边只是列举了简单的三个问题,实际面试中可能问的更深入,在并发这块我也不是什么高手,我也是一直在学习的过程中,其实在2年之前吧,我自己也录制过一套并发的课程,在我的网站猿天地上面。感兴趣的同学可以去了解下,讲了线程,线程池,锁,CountDownLatch,Semaphore等内容。

    欢迎加入我的知识星球,一起交流技术,免费学习猿天地的课程(http://cxytiandi.com/course)

    PS:目前星球中正在星主的带领下组队学习Sentinel,等你哦!

    微信扫码加入猿天地知识星球

    猿天地

  • 相关阅读:
    java类继承总结一 父类类型与子类类型之间的转化问题(转)
    将子类对象引用赋值给超类对象 JAVA 编译时多态性
    JAVA访问控制变量、类变量、类方法
    java传递是引用的拷贝,既不是引用本身,更不是对象
    JAVA的StringBuffer类
    (文件名.JAVA)的文件名只能与该文件中的public类的名称一致
    类变量(静态变量)的值不能被构造函数改写
    程序启动的顺序以及实例变量相互赋值、传递拷贝的理解
    MySQL选择合适的字符集
    MySQL日期类型选择
  • 原文地址:https://www.cnblogs.com/yinjihuan/p/10464217.html
Copyright © 2011-2022 走看看