设计模式-生产者消费者模式(java)
生产者消费者模式:
生成者消费者模式是指通过俩个不同的任务线程完成其相应的功能,二者公用一个公有队列,生产者进行产品的生成,而消费者负责消耗产品,当生产的产品大于公有队列的大小的时候,对生产者进行阻塞,当消费者消耗了以后,队列有了空间的时候,生产者在进行生产。这样一直循环的生产,消费的模型叫做生产者与消费者模式(个人理解)
(以下代码使用Kotlin编写)
package com.design.patterns
import java.util.concurrent.ExecutorService
import java.util.concurrent.Executors
import java.util.concurrent.LinkedBlockingQueue
/**
* Created by chenpengfei on 17/8/30.
*/
object Producerconsumer{
@JvmStatic
fun main(args:Array<String>){
//创建一个线程池对象来调度生产者与消费者线程
var service: ExecutorService? = Executors.newCachedThreadPool()
//创建用来存放产品的队列对象
var storage: Storage ?= Storage()
//创建生产者线程
var producter : Producter ? = Producter("陈", storage!!)
//创建消费者线程
var comsumer1 = Consumer("李", storage!!);
//添加线程任务到线程池中进行调度
service!!.submit(producter)
service!!.submit(comsumer1)
}
//消费者线程
class Consumer:Runnable{
var name:String? = null
var storage:Storage? = null
constructor(name: String ,storage:Storage){
this.name = name
this.storage = storage
}
override fun run() {
while (true){
var product = storage!!.pop()
System.out.println(name!! + "已经消费" + product.toString())
//让消费者线程睡眠10秒,为了验证生产者生产的产品
//超过10个以后会停止生产
Thread.sleep(10000)
}
}
}
class Producter :Runnable{
var name:String? = null
var storage:Storage? = null
constructor(name: String ,storage:Storage){
this.name = name
this.storage = storage
}
override fun run() {
while (true){
var product:Product = Product(this!!.name!!,System.currentTimeMillis())
System.out.println("生产"+product.toString())
storage!!.push(product)
//设置睡眠500毫秒
Thread.sleep(500)
}
}
}
class Product{
var name:String? = null
var id:Long ? = 0
constructor(name:String, id: Long){
this.name = name
this.id= id
}
override fun toString(): String {
return name + "," + id ;
}
}
//产品队列
class Storage{
var queue : LinkedBlockingQueue<Product> = LinkedBlockingQueue<Product>(10)
fun push(product: Product){
queue!!.put(product);
}
fun pop() : Product{
return queue!!.take()
}
}
}
通过下边的代码运行结果可以发现,开始生产一个产品以后,消费者就会进行消耗,而在他的消耗过程中,生产者还一直在生产,直到
队列中元素个数 = 设置的容量+ 1 (上边代码中设置为10),
所以可以看到,会生成11个。具体原因需要看LinkedBlockingQueue源码。就不介绍了。
生产陈,1504077513951
李已经消费陈,1504077513951
生产陈,1504077514456
生产陈,1504077514961
生产陈,1504077515465
生产陈,1504077515969
生产陈,1504077516472
生产陈,1504077516976
生产陈,1504077517478
生产陈,1504077517982
生产陈,1504077518486
生产陈,1504077518990
生产陈,1504077519494
李已经消费陈,1504077514456
生产陈,1504077524456
李已经消费陈,1504077514961
生产陈,1504077534462
李已经消费陈,1504077515465
生产陈,1504077544462