Java 生产者消费者与线程池

假设有1000个任务需要处理,第一种方法:将这1000任务加到阻塞队列中,用一个分发线程去将这些任务分发到下面10个子队列中,然后每个子队列有一个线程去消费这些任务。第二种方法:直接新建个线程池,每一个任务都new 一个线程去处理,再把这新建的线程放到线程池中,依靠线程池的机制去等待排队。这两种得到的效果是不是一样的,比如花费的时间,内存之类的,总感觉第二种方式虽然鲁莽,但实际上确实简单可行,第一种方式感觉稍许复杂,但是最后达到的效果和第二种是一样的呀,请教一下这两种有什么优点和缺点。

2个回答

线程池起码没有办法解决以下问题:
(1)跨进程,跨机器,不能跨机器和进程,只能单机,没有什么实用性。
(2)队列容错和恢复,停机怎么办,程序崩溃怎么办。
(3)比较容易死锁,很难调试,而且隔离性差。

所以要用消息队列。当然,你说你就是一个职业学校的课程作业,那就用线程池好了。

你这个明显用Java自带的ThreadPoolExecutor,然后创建一个有界队列,把你的任务添加进去,同时可以控制你的任务线程个数来同时进行任务的处理。
这一个类已经很成熟,可以方便的使用
http://blog.csdn.net/java2000_wl/article/details/22097059

Csdn user default icon
上传中...
上传图片
插入图片
抄袭、复制答案,以达到刷声望分或其他目的的行为,在CSDN问答是严格禁止的,一经发现立刻封号。是时候展现真正的技术了!
其他相关推荐
怎样在多线程的生产者与消费者模式中,当执行到一定状态时终止所有线程
java线程池多线程问题 假设有多个生产者和一个消费者,此时多个生产者在一段不固定的时间以后,可以生产不定长的数组(每次重新运行都不定长,但是长度肯定是有限的)。我想每次运行中,生产者生产时,消费者只要产品队列有产品就可以消费,当生产的产品数组达到极限时,消费者消费完所有的产品,然后整个线程池终止。 例如,一次运行时,所有生产者生产完大概能产生1000条数据,我要让消费者对1000条数据处理完以后终止所有线程;第二次运行,有1200条数据,让消费者生产完1200条以后终止所有。但是,每次1000还是1200,我都无法确定。求各位大神给个思路
一个java生产者消费者代码的问题
一个生产者消费者的代码,使用lock和condition实现。 [code="java"] import java.util.concurrent.locks.Condition; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; //生产/消费者模式 public class Basket { Lock lock = new ReentrantLock(); // 产生Condition对象 Condition produced = lock.newCondition(); Condition consumed = lock.newCondition(); boolean available = false; public void produce() throws InterruptedException { lock.lock(); try { if (available) { produced.await(); // 放弃lock进入睡眠 } System.out.println(&quot;Apple produced.&quot;); available = true; consumed.signal(); // 发信号唤醒等待这个Condition的线程 } finally { lock.unlock(); } } public void consume() throws InterruptedException { lock.lock(); try { if (!available) { consumed.await(); // 放弃lock进入睡眠 } /* 吃苹果 */ System.out.println(&quot;Apple consumed.&quot;); available = false; produced.signal(); // 发信号唤醒等待这个Condition的线程 } finally { lock.unlock(); } } } [/code] [code="java"] import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; //测试用类 public class ConditionTester { public static void main(String[] args) throws InterruptedException { final Basket basket = new Basket(); // 定义一个producer Runnable producer = new Runnable() { public void run() { try { basket.produce(); } catch (InterruptedException ex) { ex.printStackTrace(); } } }; // 定义一个consumer Runnable consumer = new Runnable() { public void run() { try { basket.consume(); } catch (InterruptedException ex) { ex.printStackTrace(); } } }; // 各产生10个consumer和producer ExecutorService service = Executors.newCachedThreadPool(); for (int i = 0; i < 4; i++) service.submit(consumer); Thread.sleep(2000*2); for (int i = 0; i < 4; i++) service.submit(producer); service.shutdown(); } } [/code] 以上代码我觉的执行结果应该是一个Apple prodeced 跟着一个App consumed, 就是说如果生产一个苹果,那么它应该立即被消费掉,但是实际的执行结果却不一定,有时候的执行结果为: [code="java"] Apple produced. Apple consumed. Apple produced. Apple produced. Apple consumed. Apple consumed. Apple produced. Apple consumed. [/code] 出现了连续生产两次苹果,我想问问大牛们是这是什么原因啊?
Java线程池主动获取任务提升效率是否可行。。
公司这边有一个生产者消费者模型:定时任务每秒从redis取消息,然后交给线程池(ExecutorService)去执行。这个模型在高并发的情况下,必定出现线程池处理不过来的情况,我这边是思路是线程池在执行完一个任务后去检测目前的活跃线程数(this.getActiveCount()),如果活跃数小于最大线程数时,说明线程的任务队列已经为空,则去获取下一批Redis的数据,想问问有没有大神这样做过,安全性和效率方面如何。。
java 多线程生产者和消费者模式,怎么实现边生产边消费?
如何使用java语言开发处理一批数据,使处理时间变快,而又不遗漏数据呢??
java多线程,生产者消费者问题.
新手,在试着生产者消费者问题,刚开始的时候,SyncStack为空,但是会出现先执行c那个线程,打印出eat 0.然后才是produce: 0.jdk1.8的环境. 这个是为什么呀 ``` public class ProducerConsumer{ public static void main(String[] args){ SyncStack ss = new SyncStack(); Producer p = new Producer(ss); Consumer c = new Consumer(ss); new Thread(p).start(); new Thread(c).start(); // tp.start(); // tc.start(); } } class WoTou{ int id; WoTou(int id){ this.id = id; } public String toString(){ return "WoTou: "+id; } } class SyncStack{ int index = 0; WoTou[] arrWT = new WoTou[6]; public synchronized void push(WoTou wt){ if(index==arrWT.length){ try{ this.wait(); }catch(InterruptedException e){ e.printStackTrace(); } } this.notify(); arrWT[index] = wt; index++; } public synchronized WoTou pop(){ if(index == 0){ try{ this.wait(); }catch(InterruptedException e){ e.printStackTrace(); } } this.notify(); index--; return arrWT[index]; } } class Producer implements Runnable{ SyncStack ss = null; Producer(SyncStack ss){ this.ss = ss; } public void run(){ for(int i = 0;i<20;i++){ WoTou wt = new WoTou(i); ss.push(wt); System.out.println("produce: "+wt); try{ // Thread.sleep((int)(Math.random()*1000)); Thread.sleep(1000); }catch(InterruptedException e){ e.printStackTrace(); } } } } class Consumer implements Runnable{ SyncStack ss = null; Consumer(SyncStack ss){ this.ss = ss; } public void run(){ for(int i = 0;i<20;i++){ WoTou wt = ss.pop(); System.out.println("eat: "+wt); try{ // Thread.sleep((int)(Math.random()*1000)); Thread.sleep(100); }catch(InterruptedException e){ e.printStackTrace(); } } } } ```
生产者与消费者问题(JAVA实现)
``` public class TestProducerConsumer{ public static void main(String[] agrs){ SyncStack ss = new SyncStack(); Producer p = new Producer(ss); ConSumer c = new ConSumer(ss); new Thread(p).start(); new Thread(c).start(); } } class Woto{ int id; public Woto(int id){ this.id = id; } public String toString(){ return "Woto:" + id; } } class SyncStack{ int index = 0; Woto[] w = new Woto[8]; public synchronized void push(Woto wt){ while(index == w.length){ try { this.wait(); } catch (InterruptedException e) { e.printStackTrace(); } } this.notify(); w[index] = wt; index++; } public synchronized Woto pop(){ while(index == 0){ try { this.wait(); } catch (InterruptedException e) { e.printStackTrace(); } } this.notify(); index--; return w[index]; } } class Producer implements Runnable{ SyncStack ss = null; public Producer(SyncStack ss){ this.ss = ss; } public void run() { for(int i = 0;i<10;i++){ Woto wt = new Woto(i); ss.push(wt); System.out.println("生产了="+wt); try { Thread.sleep((int) (Math.random() * 200)); } catch (InterruptedException e) { e.printStackTrace(); } } } } class ConSumer implements Runnable{ SyncStack ss = null; public ConSumer(SyncStack ss){ this.ss = ss; } public void run() { for(int i = 0;i<10;i++){ Woto wt =ss.pop(); System.out.println("消费了="+wt); try { Thread.sleep((int) (Math.random() * 1000)); } catch (InterruptedException e) { e.printStackTrace(); } } } } ``` 为什么会先出现消费者呢 ?求大神解答 ![图片说明](https://img-ask.csdn.net/upload/201508/10/1439197857_758696.png) 这里很明显是先start生产者 怎么可能先消费者呢 new Thread(p).start(); new Thread(c).start();
关于Java线程通讯,为什么生产者的p和消费者p是同一个对象?
``` class Product{ String name; //名字 double price; //价格 boolean flag = false; //产品是否生产完毕的标识,默认情况是没有生产完成。 } //生产者 class Producer extends Thread{ Product p ; //产品 public Producer(Product p) { this.p = p ; } @Override public void run() { int i = 0 ; while(true){ synchronized (p) { if(p.flag==false){ if(i%2==0){ p.name = "苹果"; p.price = 6.5; }else{ p.name="香蕉"; p.price = 2.0; } System.out.println("生产者生产出了:"+ p.name+" 价格是:"+ p.price); p.flag = true; i++; p.notifyAll(); //唤醒消费者去消费 }else{ //已经生产 完毕,等待消费者先去消费 try { p.wait(); //生产者等待 } catch (InterruptedException e) { e.printStackTrace(); } } } } } } //消费者 class Customer extends Thread{ Product p; public Customer(Product p) { this.p = p; } @Override public void run() { while(true){ synchronized (p) { if(p.flag==true){ //产品已经生产完毕 System.out.println("消费者消费了"+p.name+" 价格:"+ p.price); p.flag = false; p.notifyAll(); // 唤醒生产者去生产 }else{ //产品还没有生产,应该 等待生产者先生产。 try { p.wait(); //消费者也等待了... } catch (InterruptedException e) { e.printStackTrace(); } } } } } } public class Demo5 { public static void main(String[] args) { Product p = new Product(); //产品 //创建生产对象 Producer producer = new Producer(p); //创建消费者 Customer customer = new Customer(p); //调用start方法开启线程 producer.start(); customer.start(); } } ``` p可以不同名吗
为什么只显示生产者线程,不显示消费者线程啊?
/* * 描述生产者和消费者问题 * 1.基本的描述 * 2.上一步只能执行一次,加入while循环, * 3.加入循环后,发现线程不能同步,故加入同步,经过比较,使用同步函数 * 4.使用同步函数之后,还是没有解决问题,出现只生产不消费的问题 * 5.加入信号量机制flag,使用wait(),和notify()。在使用wait时,需要使用异常声明 * 6.还是没法解决问题,查API后引入lock接口 ,使用lock代替同步 * 7.引入condition */ package lyj.java; import java.util.concurrent.locks.Condition; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; /* * 描述资源, * 包含姓名,数量 等成员属性, * 功能:生产 * 消费 */ class Resource{ //成员属性 private String name; private int num; private boolean flag=false; public String getName() { return name; } public void setName(String name) { this.name = name; } public int getNum() { return num; } public void setNum(int num) { this.num = num; } //空的构造方法 public Resource(){} //构造方法 public Resource(String name, int num) { super(); this.name = name; this.num = num; } //引入lock,并创建对象 Lock lock=new ReentrantLock(); //引入condition Condition con=lock.newCondition(); Condition pro=lock.newCondition(); //功能1:生产 public synchronized void set(){ while(true) { lock.lock(); if(flag) try{con.await();}catch(InterruptedException e){} System.out.println(Thread.currentThread().getName()+"---生产---"+num); num++; pro.signal(); lock.unlock(); } } //功能2:消费 public synchronized void out(){ while(true) { lock.lock(); if(!flag) try{pro.await();}catch(InterruptedException e){} System.out.println(Thread.currentThread().getName()+"-----消费------"+num); con.signal(); lock.unlock(); } } } /* * 描述生产者 */ class Producer implements Runnable{ private Resource r; //构造方法 public Producer(Resource r) { this.r=r; } //复写run方法 public void run() { r.set(); } } /* * 描述消费者 */ class Consumer implements Runnable{ private Resource r; //构造方法 public Consumer(Resource r) { this.r=r; } //复写run方法 public void run() { r.out(); } } public class Test8 { public static void main(String[] args) { Resource r=new Resource(); Producer pro=new Producer(r); Consumer con=new Consumer(r); Thread t1=new Thread(pro); Thread t2=new Thread(con); t1.start(); t2.start(); } }
kafka消费者速度与什么有关
@KafkaListener(topics = {"CRBKC0002.000"}) public void sendSmsInfoByBizType(String record) { } 假设单机版的kafka,就一个节点。 1、 @KafkaListener注解接受消费者,是不是等这个方法执行完。 这个消费者进程才算消费结束。是不是一个镜像这个方法同时只能执行一次?就是不能连续起多个线程执行这个方法。 2、如果接受到参数就算消费这进程结束,也就是获取这个record消费者进程就结束了,那假设生产者一秒生产100w数据进入kafka。那这边获取参数就算消费者进程消费结束,那是不是相当于瞬间连续起100w这个方法线程执行。可是tomcat就200线程。
关于线程生产者消费者的问题
下面的程序运行的时候会一上来t2消费者线程抛异常Exception in thread "t2" java.lang.ArrayIndexOutOfBoundsException: -1 因为当t2进入等待状态的时候,t4获得所有权,马上t4又进入等待状态,唤醒之前的t2,当t2被唤醒再运行的时候已经是从bag.wait();的下一行运行,所以会抛异常。 请问怎么才能避免呢?我的bag.notify()的位置是不是放的不对呢? public class PC1 { public static final int limit=3; public static void main(String[] args) { List bag=new ArrayList(); Producer p=new Producer(bag); Consumer c=new Consumer(bag); Thread t1=new Thread(p,"t1");Thread t2=new Thread(c,"t2");Thread t3=new Thread(p,"t3");Thread t4=new Thread(c,"t4"); t2.start();t4.start(); t1.start();t3.start(); } } class Producer implements Runnable { private List bag; public Producer(List bag){ this.bag=bag; } @Override public void run() { synchronized(bag){ while(true){ if(bag.size()>=PC1.limit){ bag.notify(); try {bag.wait();} catch (InterruptedException e) {e.printStackTrace();} } int curr=bag.size(); bag.add(++curr); try {Thread.sleep(100);} catch (InterruptedException e) {e.printStackTrace();} System.out.println(Thread.currentThread().getName()+" produce "+curr); } } } } class Consumer implements Runnable { private List bag; public Consumer(List bag){ this.bag=bag; } @Override public void run() { synchronized(bag){ while(true){ if(bag.size()<=0){ bag.notify(); try {bag.wait();} catch (InterruptedException e) {e.printStackTrace();} } int curr=bag.size(); bag.remove(curr-1); try {Thread.sleep(100);} catch (InterruptedException e) {e.printStackTrace();} System.out.println(Thread.currentThread().getName()+" consume "+bag.size()); } } } }
mq消费消息与dubbo的生产工程同时处于线程阻塞状态怎么解决?
mq的消费者要不断的订阅topic dubbo的生产者工程也要通过线程阻塞的方式来保证服务开启 这两者会不会有线程冲突 求解答
java的生产者消费者同步问题,已经极力模仿教材,但是还是出现问题(没有输出结果)
/*问题:感觉是出现死锁,特别对于wait()和notify(),不知道Worker.produce()的notify()能不能唤醒Worker.move()的wait()n呢?请指教! */ import java.util.ArrayList; public class Exercise22_2_Synchronized { public static void main(String[] args) { // TODO Auto-generated method stub Worker w=new Worker(); Thread p=new Thread(new Producerr(w)); Thread m=new Thread(new Moverr(w)); p.start(); m.start(); } } /*电脑类,有两个静态成员 id和available,每新建一个电脑类对象id自动加一,available变为true(可用),available用来作为新对象是否可用的标志,被拿走之后便置为false*/ class Computerr { private static int id=0; public static boolean available=false; Computerr() { id++; available=true; } public void printInformation() { System.out.println("这是第"+id+"台电脑..."); } } /*此类为生产线程,用于产生一个电脑对象(和搬运线程Moverr使用同一个电脑类操作对象w调用w.produce()方法)*/ class Producerr implements Runnable { Worker w; Producerr(Worker w) { this.w=w; } public void run() { w.produce(); } } /*此类为搬运线程,用于收纳新产生的电脑对象,使用电脑类操作对象w,调用w.move()方法*/ class Moverr implements Runnable { Worker w; Moverr(Worker w) { this.w=w; } @Override public void run() { w.move(); } } /*此类为电脑类对象的操作(具体的产生和收纳工作步骤),分别给produce和move方法加锁,达到生产与搬运间的互斥*/ class Worker { Computer cp; ArrayList<Computer> al=new ArrayList<>(); public synchronized void produce() { while(true) { if(Computerr.available==false) { cp=new Computer(); notify(); } else { try { wait(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } } } public synchronized void move() { while(true) { if(Computerr.available==true) { al.add(cp); cp.available=false; al.get(al.size()-1); notify(); } else { try { wait(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } } } }
关于生产消费线程,消费者重复执行的问题
一个关于线程的问题,生产者放入队列中后,不打断点的话,消费者线程会执行两次,打断点的话是执行一次,贴一下代码,求解答。 缓冲队列: ``` package psplat.unicorn.model; import java.util.List; import java.util.concurrent.LinkedBlockingQueue; /** * @author L * 缓冲队列 */ public class CacheQueue<T> { private LinkedBlockingQueue<T> queue = new LinkedBlockingQueue<T>(); public CacheQueue() { } protected void add(T t){ queue.add(t); } protected T remove(){ return queue.poll(); } protected T get(){ return queue.peek(); } protected boolean isEmpty(){ return queue.isEmpty(); } protected void addAll(List<T> list){ queue.addAll(list); } protected int getLength() { return queue.size(); } } ``` 缓冲队列管理类: ``` package psplat.unicorn.model; import java.util.List; import java.util.concurrent.locks.Condition; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; /** * @author L * 联通队列管理类 */ public class UnicornQueueManager { private CacheQueue<MessageSendInfo> queueCache; private Lock lock; private Condition condition; private static volatile UnicornQueueManager instance; private UnicornQueueManager(){ queueCache = new CacheQueue<MessageSendInfo>(); this.lock = new ReentrantLock(); this.condition = lock.newCondition(); } public static UnicornQueueManager getInstance(){ if(instance == null){ synchronized(UnicornQueueManager.class){ if(instance == null){ instance = new UnicornQueueManager(); } } } return instance; } public void add(MessageSendInfo messageInfo){ queueCache.add(messageInfo); lock.lock(); condition.signalAll(); lock.unlock(); } public MessageSendInfo removeOne(){ return queueCache.remove(); } public MessageSendInfo get(){ return queueCache.get(); } public boolean isEmpty(){ return queueCache.isEmpty(); } public Lock getLock() { return lock; } public Condition getCondition() { return condition; } public void addAll(List<MessageSendInfo> list){ queueCache.addAll(list); } public int getLength() { return queueCache.getLength(); } } ``` 消费者线程: ``` package psplat.unicorn.consumer; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import org.jeecgframework.web.system.service.SystemService; import org.springframework.beans.factory.InitializingBean; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; import psplat.https.HttpClientUtil; import psplat.unicorn.entity.UnicornLogEntity; import psplat.unicorn.model.MessageSendInfo; import psplat.unicorn.model.MessageStatus; import psplat.unicorn.model.ReportMapManager; import psplat.unicorn.model.UnicornConstants; import psplat.unicorn.model.UnicornQueueManager; import psplat.util.ConvertMapUtil; @Component public class UnicordSendConsumer implements InitializingBean { private ExecutorService consumerRunnable; @Autowired private SystemService systemService; //用于发送计数,发送三次,失败,则丢弃数据,否则队列后的消息全部阻塞 private static int count = 0; @Override public void afterPropertiesSet() throws Exception { consumerRunnable = Executors.newSingleThreadExecutor(); consumerRunnable.execute(new Runnable() { @Override public void run() { while(true) { if(UnicornQueueManager.getInstance().isEmpty()) { UnicornQueueManager.getInstance().getLock().lock(); try { UnicornQueueManager.getInstance().getCondition().await(); } catch (InterruptedException e) { e.printStackTrace(); } UnicornQueueManager.getInstance().getLock().unlock(); } else { MessageSendInfo sendInfo = UnicornQueueManager.getInstance().get(); //组装参数并发送 String url = UnicornConstants.COMMON_URL.getSuffix() + UnicornConstants.SEND.getSuffix(); Map<String, String> argsMap = new HashMap<String, String>(); argsMap.put("SpCode", UnicornConstants.SpCode.getSuffix()); argsMap.put("LoginName", UnicornConstants.LoginName.getSuffix()); argsMap.put("Password", UnicornConstants.Password.getSuffix()); argsMap.put("MessageContent", sendInfo.getMessageContent()); argsMap.put("UserNumber", sendInfo.getNumbers()); argsMap.put("SerialNumber", sendInfo.getSerialNumber()); String result = (new HttpClientUtil()).doPost(url, argsMap, "GBK"); String resultCode = ConvertMapUtil.convertMapFromArgs(result).get("result"); if(!resultCode.equals("0")) { //发送失败,发三次,移除 count++; if(count != 3) { //失败了,1秒后重新发送 this.threadSleep(1000); continue; } } count = 0; UnicornQueueManager.getInstance().removeOne(); System.out.println("执行,此时队列长度" + UnicornQueueManager.getInstance().getLength()); List<UnicornLogEntity> logs = sendInfo.inrichUnicornLogs(MessageStatus.COMMIT.getCode(), resultCode); systemService.batchSave(logs); ReportMapManager.getInstance().addAll(ReportConsumer.convertUnicornLogEntityMap(logs)); } } } private void threadSleep(int i) { try { Thread.sleep(i); } catch (InterruptedException e) { e.printStackTrace(); } } }); } } ``` 有大神看出来为何这个线程会执行两次么?加了打印之后,队列长度已经为0为什么不进入等待? 如下是打印: 调用结束,返回值:result=0&description=发送短信成功&taskid=208754669702&faillist=&task_id=208754669702 执行,此时队列长度0 调用结束,返回值:result=0&description=发送短信成功&taskid=208753973775&faillist=&task_id=208753973775 执行,此时队列长度0 求指导!
Java多线程并发如何模拟
一个Java Application运行后,在系统中是作为一 个线程吗?运行main方法以后,为什么不能实现多个线程启动?我想用java程序模拟多个消费者和kafka生产者通信,可以实现吗 import org.apache.kafka.clients.consumer.ConsumerRecord; import org.apache.kafka.clients.consumer.ConsumerRecords; import org.apache.kafka.clients.consumer.KafkaConsumer; import java.util.Arrays; import java.util.Properties; /** * Created by Administrator on 2016/10/17. */ public class consumerTest extends Thread{ public synchronized void run(){ Properties props = new Properties(); props.put("bootstrap.servers", "localhost:9092"); //消费者组group props.put("group.id", "test"); //是否自动确认offset props.put("enable.auto.commit", "true"); //自动确认offset的时间间隔 props.put("auto.commit.interval.ms", "1000"); //会话超时时间 props.put("session.timeout.ms", "30000"); //key的序列化类 props.put("key.deserializer", "org.apache.kafka.common.serialization.StringDeserializer"); //value的序列化类 props.put("value.deserializer", "org.apache.kafka.common.serialization.StringDeserializer"); KafkaConsumer<String, String> consumer = new KafkaConsumer<String, String>(props); //消费者订阅的topic, 可同时订阅多个 consumer.subscribe(Arrays.asList("test")); while (true) { //读取数据,读取超时时间为100ms ConsumerRecords<String, String> records = consumer.poll(100); for (ConsumerRecord<String, String> record : records) System.out.println(String.format("offset = %d, key = %s, value = %s", record.offset(), record.key(), record.value())); } } public static void main(String[] args) { consumerTest test1=new consumerTest(); Thread threads[] = new Thread[5]; for (int i = 0; i < threads.length; i++) threads[i] = new Thread(test1); for (int i = 0; i < threads.length; i++) { threads[i].start(); } } }
Java串口通信,利用线程池实现接收数据及处理数据,但是数据包会丢数据
public void serialEvent(SerialPortEvent event) { switch (event.getEventType()) { case SerialPortEvent.BI: case SerialPortEvent.OE: case SerialPortEvent.FE: case SerialPortEvent.PE: case SerialPortEvent.CD: case SerialPortEvent.CTS: case SerialPortEvent.DSR: case SerialPortEvent.RI: case SerialPortEvent.OUTPUT_BUFFER_EMPTY: break; case SerialPortEvent.DATA_AVAILABLE: readBuffer1 = new byte[90]; Runnable insert1 = new Runnable(){ public void run(){ synchronized (queue) { //读取接收的数据 try { while (inputStream1.available() > 0) { inputStream1.read(readBuffer1); queue.put(readBuffer1); } } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } } }; executorService.execute(insert1);//生产者 executorService.execute(new PacketReturn1());//消费者
ArrayBlockingQueue.poll出现Cpu 100%
异常如下: 生产者线程,较多,其中一个栈如下 "http-thread-pool-8090(1) SelectorRunner" daemon prio=10 tid=0x00007f70c001b800 nid=0x3bb waiting on condition [0x00007f71b45ce000] java.lang.Thread.State: WAITING (parking) at sun.misc.Unsafe.park(Native Method) - parking to wait for <0x0000000702989fd8> (a java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject) at java.util.concurrent.locks.LockSupport.park(LockSupport.java:186) at java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject.await(AbstractQueuedSynchronizer.java:2043) at java.util.concurrent.ArrayBlockingQueue.put(ArrayBlockingQueue.java:324) 消费者线程,只有一个,线程栈如下: "Async-Log-Thread" prio=10 tid=0x00007f71d4ade800 nid=0x3b0 runnable [0x00007f71b51ed000] java.lang.Thread.State: RUNNABLE at java.lang.Thread.yield(Native Method) at java.util.concurrent.locks.AbstractQueuedSynchronizer.transferAfterCancelledWait(AbstractQueuedSynchronizer.java:1709) at java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject.awaitNanos(AbstractQueuedSynchronizer.java:2079) at java.util.concurrent.ArrayBlockingQueue.poll(ArrayBlockingQueue.java:389) http-thread-pool线程向ArrayBlockingQueue队列中写入,put操作卡住了。 说明这里队列满了,但发现对应用消费线程却卡用poll操作上。但又不是 hang死,cpu很高,该问题有没有什么解决思路? 各路大神,请帮助。
Java多线程,生产消费问题
package thread; public class Producer_ConsumerTest { public static void main(String[] args) { SyncStack ss = new SyncStack(); Thread producter = new Producter(ss); Thread consumer = new Consumer(ss); producter.start(); consumer.start(); } } class SyncStack { private int total = 0; private boolean flag = false; synchronized void product() { while(flag == true) { try { this.wait(); } catch (InterruptedException e) { e.printStackTrace(); } } total++; flag = true; this.notify(); } synchronized int conmuse() { while(flag == false) { try { this.wait(); } catch (InterruptedException e) { e.printStackTrace(); } } total--; flag = false; this.notify(); return total; } } class Producter extends Thread { SyncStack ss; Producter(SyncStack ss) { this.ss = ss; } public void run() { for(int i=1;i<10;i++) { ss.product(); System.out.println("生产者" + Thread.currentThread().getName() + "生产了第" + i + "个商品,商品总数为"); } } } class Consumer extends Thread { SyncStack ss; Consumer(SyncStack ss) { this.ss = ss; } public void run() { for(int i=1;i<10;i++) { ss.conmuse(); System.out.println("消费者" + Thread.currentThread().getName() + "消费了第" + i + "个商品总数为"); } } } ----------------- [b]我希望的输出结果是生产1个,然后消费1个,生产在前,但是达不到要求,目前实际输出是无序的,哪位朋友能帮忙修改一下吗?[/b]
关于Condition与线程绑定的问题
正在自学java,在多线程部分看到Lock与Condition部分的内容,有点不明白。 ```//通过已有的锁获取两组监视器,一组监视生产者,一组监视消费者。 Condition producer_con = lock.newCondition(); Condition consumer_con = lock.newCondition(); public void set(String name) { lock.lock(); try { while(flag) //若有烤鸭,就不生产 try{producer_con.await();}catch(InterruptedException e){} this.name = name + count; count++; System.out.println(Thread.currentThread().getName()+"...生产者..."+this.name); flag = true; consumer_con.signal(); } finally {lock.unlock();} } ``` 我不明白,Condition对象与线程是怎么绑定的?难道是,某个线程是由哪个Condition对象调用await()阻塞的,就由哪个Condition对象唤醒?那么因为没有获取锁而自动阻塞的线程又怎么解释?
生产者和消费者的问题 请教了
下面的程序有点小小问题,先放出问题 求解,下面附上代码 [quote] 期望运行结果: ....//省略了 46 生产者gen03馒头 编号:3 47 生产者gen02馒头 编号:4 48 生产者gen01馒头 编号:5 49 --消费者cus01馒头 编号:5 50 生产者gen03馒头 编号:5 51 生产者gen01馒头 编号:6 生产者gen02馒头 编号:7 53 53 生产者gen03馒头 编号:8 54 生产者gen01馒头 编号:9 55 生产者gen02馒头 编号:10 56 ********************************************************* 问题点:(注掉了//--------------包围的代码产生的) ....//省略了 48 --消费者cus01馒头 编号:12 49 --消费者cus02馒头 编号:11 50 --消费者cus01馒头 编号:10 51 生产者gen03馒头 编号:10 52 生产者gen02馒头 编号:11 53 生产者gen01馒头 编号:12 54 生产者gen02馒头 编号:13 55 生产者gen01馒头 编号:14 56 生产者gen03馒头 编号:15 57 生产者gen02馒头 编号:16 58 生产者gen03馒头 编号:17 59 生产者gen01馒头 编号:18 60 生产者gen03馒头 编号:19 61 生产者gen02馒头 编号:20 生产者gen01馒头 编号:21 63 63 [/quote] 上代码 [code="java"] package com.ibm.TestSynchronized; import java.util.ArrayList; public class Generant_Customer { public static void main(String[] args) { Collection c = new Collection(); Generant gen = new Generant(c); Customer cus = new Customer(c); new Thread(gen,"gen01").start(); new Thread(gen,"gen02").start(); new Thread(gen,"gen03").start(); new Thread(cus,"cus01").start(); new Thread(cus,"cus02").start(); } } /** * 资源类 , 消费者和生产者共同操作的资源 */ class Collection { ArrayList<String> collection = new ArrayList<String>(); static final int length = 10; int index = 1 ; int operateCount = 0; /* 生产者生产 */ public synchronized void add(){ if(collection.size()>=length){ try { wait(); } catch (InterruptedException e) { System.out.println("add() has been interrupted !"); System.exit(1); } } notifyAll();//唤醒在此对象监视器上等待的单个线程 collection.add("馒头 编号:"+index); System.out.println("生产者" +Thread.currentThread().getName() + collection.get(index-1)); index ++ ; operateCount++; } /* 消费者消费 */ public synchronized void pop(){ if(collection.size() == 0){ try { wait(); } catch (InterruptedException e) { System.out.println("pop() has been interrupted !"); System.exit(1); } } notifyAll(); //唤醒在此对象监视器上等待的单个线程 System.out.println("--消费者" +Thread.currentThread().getName() + collection.get(collection.size()-1)); collection.remove(collection.size()-1); index -- ; operateCount++; } } class Generant implements Runnable{ Collection coll = null ; public Generant(Collection collection ){ this.coll = collection ; } /* 生产者开始执行 */ public void run() { while(true){ coll.add(); System.out.println(coll.operateCount); //------------------------------------------------------------------ //注掉后运行就有问题 try { Thread.sleep(200); } catch (InterruptedException e) { System.out.println("Generant.run() has been interrupted !\\n" + " System continue..."); } //------------------------------------------------------------------ } } } class Customer implements Runnable{ Collection coll = null ; /* 线程开关 */ boolean doRun = true ; public Customer(Collection collection ){ this.coll = collection ; } /* 消费者开始执行 */ public void run() { while(doRun){ coll.pop(); System.out.println(coll.operateCount); //------------------------------------------------------------------ //注掉后运行就有问题 try { Thread.sleep(150); } catch (InterruptedException e) { System.out.println("Customer.run() has been interrupted !\\n" + " System continue..."); } //------------------------------------------------------------------ if(coll.operateCount == 50){ doRun = false; } } } } [/code]
相见恨晚的超实用网站
搞学习 知乎:www.zhihu.com 简答题:http://www.jiandati.com/ 网易公开课:https://open.163.com/ted/ 网易云课堂:https://study.163.com/ 中国大学MOOC:www.icourse163.org 网易云课堂:study.163.com 哔哩哔哩弹幕网:www.bilibili.com 我要自学网:www.51zxw
花了20分钟,给女朋友们写了一个web版群聊程序
参考博客 [1]https://www.byteslounge.com/tutorials/java-ee-html5-websocket-example
爬虫福利二 之 妹子图网MM批量下载
爬虫福利一:27报网MM批量下载    点击 看了本文,相信大家对爬虫一定会产生强烈的兴趣,激励自己去学习爬虫,在这里提前祝:大家学有所成! 目标网站:妹子图网 环境:Python3.x 相关第三方模块:requests、beautifulsoup4 Re:各位在测试时只需要将代码里的变量 path 指定为你当前系统要保存的路径,使用 python xxx.py 或IDE运行即可。
字节跳动视频编解码面经
引言 本文主要是记录一下面试字节跳动的经历。 三四月份投了字节跳动的实习(图形图像岗位),然后hr打电话过来问了一下会不会opengl,c++,shador,当时只会一点c++,其他两个都不会,也就直接被拒了。 七月初内推了字节跳动的提前批,因为内推没有具体的岗位,hr又打电话问要不要考虑一下图形图像岗,我说实习投过这个岗位不合适,不会opengl和shador,然后hr就说秋招更看重基础。我当时
Java学习的正确打开方式
在博主认为,对于入门级学习java的最佳学习方法莫过于视频+博客+书籍+总结,前三者博主将淋漓尽致地挥毫于这篇博客文章中,至于总结在于个人,实际上越到后面你会发现学习的最好方式就是阅读参考官方文档其次就是国内的书籍,博客次之,这又是一个层次了,这里暂时不提后面再谈。博主将为各位入门java保驾护航,各位只管冲鸭!!!上天是公平的,只要不辜负时间,时间自然不会辜负你。 何谓学习?博主所理解的学习,它
程序员必须掌握的核心算法有哪些?
由于我之前一直强调数据结构以及算法学习的重要性,所以就有一些读者经常问我,数据结构与算法应该要学习到哪个程度呢?,说实话,这个问题我不知道要怎么回答你,主要取决于你想学习到哪些程度,不过针对这个问题,我稍微总结一下我学过的算法知识点,以及我觉得值得学习的算法。这些算法与数据结构的学习大多数是零散的,并没有一本把他们全部覆盖的书籍。下面是我觉得值得学习的一些算法以及数据结构,当然,我也会整理一些看过
大学四年自学走来,这些私藏的实用工具/学习网站我贡献出来了
大学四年,看课本是不可能一直看课本的了,对于学习,特别是自学,善于搜索网上的一些资源来辅助,还是非常有必要的,下面我就把这几年私藏的各种资源,网站贡献出来给你们。主要有:电子书搜索、实用工具、在线视频学习网站、非视频学习网站、软件下载、面试/求职必备网站。 注意:文中提到的所有资源,文末我都给你整理好了,你们只管拿去,如果觉得不错,转发、分享就是最大的支持了。 一、电子书搜索 对于大部分程序员...
linux系列之常用运维命令整理笔录
本博客记录工作中需要的linux运维命令,大学时候开始接触linux,会一些基本操作,可是都没有整理起来,加上是做开发,不做运维,有些命令忘记了,所以现在整理成博客,当然vi,文件操作等就不介绍了,慢慢积累一些其它拓展的命令,博客不定时更新 顺便拉下票,我在参加csdn博客之星竞选,欢迎投票支持,每个QQ或者微信每天都可以投5票,扫二维码即可,http://m234140.nofollow.ax.
比特币原理详解
一、什么是比特币 比特币是一种电子货币,是一种基于密码学的货币,在2008年11月1日由中本聪发表比特币白皮书,文中提出了一种去中心化的电子记账系统,我们平时的电子现金是银行来记账,因为银行的背后是国家信用。去中心化电子记账系统是参与者共同记账。比特币可以防止主权危机、信用风险。其好处不多做赘述,这一层面介绍的文章很多,本文主要从更深层的技术原理角度进行介绍。 二、问题引入 假设现有4个人...
Python 基础(一):入门必备知识
目录1 标识符2 关键字3 引号4 编码5 输入输出6 缩进7 多行8 注释9 数据类型10 运算符10.1 常用运算符10.2 运算符优先级 1 标识符 标识符是编程时使用的名字,用于给变量、函数、语句块等命名,Python 中标识符由字母、数字、下划线组成,不能以数字开头,区分大小写。 以下划线开头的标识符有特殊含义,单下划线开头的标识符,如:_xxx ,表示不能直接访问的类属性,需通过类提供
这30个CSS选择器,你必须熟记(上)
关注前端达人,与你共同进步CSS的魅力就是让我们前端工程师像设计师一样进行网页的设计,我们能轻而易举的改变颜色、布局、制作出漂亮的影音效果等等,我们只需要改几行代码,不需...
国产开源API网关项目进入Apache孵化器:APISIX
点击蓝色“程序猿DD”关注我回复“资源”获取独家整理的学习资料!近日,又有一个开源项目加入了这个Java开源界大名鼎鼎的Apache基金会,开始进行孵化器。项目名称:AP...
程序员接私活怎样防止做完了不给钱?
首先跟大家说明一点,我们做 IT 类的外包开发,是非标品开发,所以很有可能在开发过程中会有这样那样的需求修改,而这种需求修改很容易造成扯皮,进而影响到费用支付,甚至出现做完了项目收不到钱的情况。 那么,怎么保证自己的薪酬安全呢? 我们在开工前,一定要做好一些证据方面的准备(也就是“讨薪”的理论依据),这其中最重要的就是需求文档和验收标准。一定要让需求方提供这两个文档资料作为开发的基础。之后开发
网页实现一个简单的音乐播放器(大佬别看。(⊙﹏⊙))
今天闲着无事,就想写点东西。然后听了下歌,就打算写个播放器。 于是乎用h5 audio的加上js简单的播放器完工了。 欢迎 改进 留言。 演示地点跳到演示地点 html代码如下`&lt;!DOCTYPE html&gt; &lt;html&gt; &lt;head&gt; &lt;title&gt;music&lt;/title&gt; &lt;meta charset="utf-8"&gt
Python十大装B语法
Python 是一种代表简单思想的语言,其语法相对简单,很容易上手。不过,如果就此小视 Python 语法的精妙和深邃,那就大错特错了。本文精心筛选了最能展现 Python 语法之精妙的十个知识点,并附上详细的实例代码。如能在实战中融会贯通、灵活使用,必将使代码更为精炼、高效,同时也会极大提升代码B格,使之看上去更老练,读起来更优雅。 1. for - else 什么?不是 if 和 else 才
数据库优化 - SQL优化
前面一篇文章从实例的角度进行数据库优化,通过配置一些参数让数据库性能达到最优。但是一些“不好”的SQL也会导致数据库查询变慢,影响业务流程。本文从SQL角度进行数据库优化,提升SQL运行效率。 判断问题SQL 判断SQL是否有问题时可以通过两个表象进行判断: 系统级别表象 CPU消耗严重 IO等待严重 页面响应时间过长
2019年11月中国大陆编程语言排行榜
2019年11月2日,我统计了某招聘网站,获得有效程序员招聘数据9万条。针对招聘信息,提取编程语言关键字,并统计如下: 编程语言比例 rank pl_ percentage 1 java 33.62% 2 c/c++ 16.42% 3 c_sharp 12.82% 4 javascript 12.31% 5 python 7.93% 6 go 7.25% 7
通俗易懂地给女朋友讲:线程池的内部原理
餐厅的约会 餐盘在灯光的照耀下格外晶莹洁白,女朋友拿起红酒杯轻轻地抿了一小口,对我说:“经常听你说线程池,到底线程池到底是个什么原理?”我楞了一下,心里想女朋友今天是怎么了,怎么突然问出这么专业的问题,但做为一个专业人士在女朋友面前也不能露怯啊,想了一下便说:“我先给你讲讲我前同事老王的故事吧!” 大龄程序员老王 老王是一个已经北漂十多年的程序员,岁数大了,加班加不动了,升迁也无望,于是拿着手里
经典算法(5)杨辉三角
杨辉三角 是经典算法,这篇博客对它的算法思想进行了讲解,并有完整的代码实现。
编写Spring MVC控制器的14个技巧
本期目录 1.使用@Controller构造型 2.实现控制器接口 3.扩展AbstractController类 4.为处理程序方法指定URL映射 5.为处理程序方法指定HTTP请求方法 6.将请求参数映射到处理程序方法 7.返回模型和视图 8.将对象放入模型 9.处理程序方法中的重定向 10.处理表格提交和表格验证 11.处理文件上传 12.在控制器中自动装配业务类 ...
腾讯算法面试题:64匹马8个跑道需要多少轮才能选出最快的四匹?
昨天,有网友私信我,说去阿里面试,彻底的被打击到了。问了为什么网上大量使用ThreadLocal的源码都会加上private static?他被难住了,因为他从来都没有考虑过这个问题。无独有偶,今天笔者又发现有网友吐槽了一道腾讯的面试题,我们一起来看看。 腾讯算法面试题:64匹马8个跑道需要多少轮才能选出最快的四匹? 在互联网职场论坛,一名程序员发帖求助到。二面腾讯,其中一个算法题:64匹
面试官:你连RESTful都不知道我怎么敢要你?
面试官:了解RESTful吗? 我:听说过。 面试官:那什么是RESTful? 我:就是用起来很规范,挺好的 面试官:是RESTful挺好的,还是自我感觉挺好的 我:都挺好的。 面试官:… 把门关上。 我:… 要干嘛?先关上再说。 面试官:我说出去把门关上。 我:what ?,夺门而去 文章目录01 前言02 RESTful的来源03 RESTful6大原则1. C-S架构2. 无状态3.统一的接
求小姐姐抠图竟遭白眼?痛定思痛,我决定用 Python 自力更生!
点击蓝色“Python空间”关注我丫加个“星标”,每天一起快乐的学习大家好,我是 Rocky0429,一个刚恰完午饭,正在用刷网页浪费生命的蒟蒻...一堆堆无聊八卦信息的网页内容慢慢使我的双眼模糊,一个哈欠打出了三斤老泪,就在此时我看到了一张图片:是谁!是谁把我女朋友的照片放出来的!awsl!太好看了叭...等等,那个背景上的一堆鬼画符是什么鬼?!真是看不下去!叔叔婶婶能忍,隔壁老王的三姨妈的四表...
为啥国人偏爱Mybatis,而老外喜欢Hibernate/JPA呢?
关于SQL和ORM的争论,永远都不会终止,我也一直在思考这个问题。昨天又跟群里的小伙伴进行了一番讨论,感触还是有一些,于是就有了今天这篇文。 声明:本文不会下关于Mybatis和JPA两个持久层框架哪个更好这样的结论。只是摆事实,讲道理,所以,请各位看官勿喷。 一、事件起因 关于Mybatis和JPA孰优孰劣的问题,争论已经很多年了。一直也没有结论,毕竟每个人的喜好和习惯是大不相同的。我也看
SQL-小白最佳入门sql查询一
不要偷偷的查询我的个人资料,即使你再喜欢我,也不要这样,真的不好;
项目中的if else太多了,该怎么重构?
介绍 最近跟着公司的大佬开发了一款IM系统,类似QQ和微信哈,就是聊天软件。我们有一部分业务逻辑是这样的 if (msgType = "文本") { // dosomething } else if(msgType = "图片") { // doshomething } else if(msgType = "视频") { // doshomething } else { // doshom...
致 Python 初学者
欢迎来到“Python进阶”专栏!来到这里的每一位同学,应该大致上学习了很多 Python 的基础知识,正在努力成长的过程中。在此期间,一定遇到了很多的困惑,对未来的学习方向感到迷茫。我非常理解你们所面临的处境。我从2007年开始接触 python 这门编程语言,从2009年开始单一使用 python 应对所有的开发工作,直至今天。回顾自己的学习过程,也曾经遇到过无数的困难,也曾经迷茫过、困惑过。开办这个专栏,正是为了帮助像我当年一样困惑的 Python 初学者走出困境、快速成长。希望我的经验能真正帮到你
“狗屁不通文章生成器”登顶GitHub热榜,分分钟写出万字形式主义大作
一、垃圾文字生成器介绍 最近在浏览GitHub的时候,发现了这样一个骨骼清奇的雷人项目,而且热度还特别高。 项目中文名:狗屁不通文章生成器 项目英文名:BullshitGenerator 根据作者的介绍,他是偶尔需要一些中文文字用于GUI开发时测试文本渲染,因此开发了这个废话生成器。但由于生成的废话实在是太过富于哲理,所以最近已经被小伙伴们给玩坏了。 他的文风可能是这样的: 你发现,...
程序员:我终于知道post和get的区别
是一个老生常谈的话题,然而随着不断的学习,对于以前的认识有很多误区,所以还是需要不断地总结的,学而时习之,不亦说乎
《程序人生》系列-这个程序员只用了20行代码就拿了冠军
你知道的越多,你不知道的越多 点赞再看,养成习惯GitHub上已经开源https://github.com/JavaFamily,有一线大厂面试点脑图,欢迎Star和完善 前言 这一期不算《吊打面试官》系列的,所有没前言我直接开始。 絮叨 本来应该是没有这期的,看过我上期的小伙伴应该是知道的嘛,双十一比较忙嘛,要值班又要去帮忙拍摄年会的视频素材,还得搞个程序员一天的Vlog,还要写BU...
相关热词 c# clr dll c# 如何orm c# 固定大小的字符数组 c#框架设计 c# 删除数据库 c# 中文文字 图片转 c# 成员属性 接口 c#如何将程序封装 16进制负数转换 c# c#练手项目
立即提问