Java实现一个简单的线程池

我们知道java.util.concurrent包下有个Executors类,这个类提供了一系列静态方法来创建各种线程池,例如newCachedThreadPool(), newFixedThreadPool()等等。参照ThreadPoolExecutor类的功能,我们知道,一个线程池所需要实现的功能和接口大致是:(1)维护一个任务队列,客户端可以提交Runnable任务到这个队列中(2)初始化…

more >>

使用DelayQueue实现缓存

实现一个缓存其实就是需要实现一个能够存储键值对,并自动清理超时缓存项的数据结构。java.util.concurrent包下有个DelayQueue,它是一个无界的BlockingQueue,存入DelayQueue的对象必须实现Delayed接口。DelayQueue提供一个阻塞的take方法,只有过期的Delayed对象才能被take出队列。利用DelayQueue的这个特性,我们可以用Del…

more >>

Java实现读写锁

实现一个简单的读写锁我们知道,使用读写锁的目的是使读操作共享一个锁,写操作独占一个锁,从而使得多个读操作可以同时进行,而进行写操作时才实现互斥,当读操作比较频繁时,可以减少加锁释放锁带来的消耗。我之前的博文有介绍到ReentrantReadWriteLock的使用,其实我们完全可以自己实现一个读写锁。首先我们必须理解读写锁的一些规则:(1) 加读锁之前,必须检查当前是否已经有写操作,或者有写操作的…

more >>

ReadWriteLock读写锁

我们知道,通过Java的synchronized关键字获得的锁是排他锁,当一个线程获得对象的排他锁,不管该线程执行的是读操作还是写操作,其他线程都只能等待直到对象锁被释放。然而,考虑这样一种情况,当有多个线程读取一个共享资源而只有一个线程对共享资源发生修改操作,对于读操作我们就没必要使用排他锁,我们可以使用共享锁,使得执行读操作的线程可以共享对象锁,并发地进行读取。只有写操作发生时,线…

more >>

同步辅助类CountdownLatch与CyclicBarrier

JDK5以后java.util.concurrent包下引入了大量解决并发问题的新类,其中比较常用的两个并发辅助类就是CountDownLatch和CyclicBarrierCountdownLatch当一个或多个线程需要等待其他线程完成后才执行,这时候可以用CountdownLatch来实现。CountdownLatch初始化时可以指定一个计数,代表执行的线程个数。Countdown…

more >>

并发编程之任务协作

前言 当多个线程共享资源时,我们通常利用加锁的方式来避免一个线程对资源的操作影响另一线程对该资源的操作,例如使用synchronized关键字或Lock对象。而如果多个线程之间的关系不是互斥,而是协作完成某种任务,例如煮面,需要先把水烧开,再加面,然后加调料,又例如典型的生产者消费者问题。对于这种协作关系的多个线程,关键在于线程之间的握手或者说是通信,确保一个任务执行完之后能将信号传递…

more >>

Servlet的线程安全问题

Servlet是线程安全的吗? 答案是否定的。这是由于Servlet在tomcat中是以单例模式存在的,也就是说,当客户端第一次请求servlet,tomcat容器会根据web.xml生成对应的servlet实例,当客户端第二次请求同一个servlet,tomcat容器不会再生成新的。因此,不同请求共享同一个servlet实例的资源,从而导致线程不安全的问题。 Servlet…

more >>