0 0

java 信号量 semaphore 解决以下问题?0

有这样一个需求,一个线程T1不停创建对象,放到数组中,数组的长度为5,当数组满了以后就将这个数组放到另一个线程线程T2,由T2将数组里的对象存到数据库中。而T1继续创建另一个数组,重复上面的操作。T2除了接收到数组,然后将数组入库以外,还有一个功能是定时5秒中做一个入库操作,5秒钟以后,不管T1创建的数组是否满5个(数组的长度为5),都要将正在创建的数组发送给T2为T2做入库操作。也就是T2接收的数组时要入库,等待5秒以后不管T1的数组是否满5个也要入库,用java 信号量 semaphore怎么做,只有T1,T2两个线程。如果不用 semaphore我也以使用生产者消费者轻松实现,但领导非要用信号量 semaphore来做,大家看怎么做?谢谢!
2012年8月24日 01:22

8个答案 按时间排序 按投票排序

0 0

hello,以前用观察模式做了一个引擎日志的功能,到五个执行入库时用的观察者,在添加的时候,看一下size,如果size>=5就入库。定时使用Timer,5秒钟执行以下,如果size>=5就入库。

关于同步问题,我是把添加记录和定时检查的有效代码同步的,要是嫌入库需要时间太长,我是在单起一个thread,然后复制你的数组传进去的。

至于countDownLatch,cyclicBarrier,还有你说的信号灯都没用上,同步就是synchronize的一个object

2012年10月29日 16:46
0 0

Java中Semaphore不能满足你的需求。
Semaphore管理一个有效的许可,类似令牌环网那个原理,如果你要控制一个资源只允许N个线程访问,这个可以使用Semaphore。

另外一个概念Latch能满足你的要求,在Java对应的实现是CountDownLatch,你可以查一下。也可以参考这个资料:
"Java concurrecncy in Practice". 5.5 Synchronizer.

2012年8月24日 14:58
0 0

引用
[img][/img][url][/url][flash=200,200][/flash]

2012年8月24日 14:28
0 0

单独用信号量控制不了 刚才做了简单的实验
package cn.yzc.thread;

import java.util.Arrays;
import java.util.Random;
import java.util.concurrent.Semaphore;

/**
* @author Yao Zhichao
* @Function:
* @CreateDate :2012-8-24
* @ModifyRecord :
*/
public class SemaphoreTest {
public static final int MAX_AVAILABLE = 1;
public static final Semaphore available = new Semaphore(MAX_AVAILABLE);
public static final String[]  dataStr = new String[5];

public static void main(String[] args) {
new Thread(new T1(available, dataStr)).start();
new Thread(new T2(available, dataStr)).start();
System.out.println("main thread end*");

}
}

class T1 implements Runnable {
private Semaphore available;
private String[]  dataStr;
public T1(){}

public T1(Semaphore available, String[]  dataStr) {
this.available = available;
this.dataStr = dataStr;
}

@Override
public void run() {
while(true) {
try {
//获取信号量
available.acquire();

for(int i=0; i<dataStr.length; i++) {
dataStr[i] = getRandString();
}

System.out.println(this.getClass().getSimpleName() + "--------" + Arrays.asList(dataStr));
} catch (InterruptedException e) {
e.printStackTrace();
} finally {
//释放信号量
available.release();
}
}
}

public String getRandString(){
String str = "abcdefghijklmnopqrstuvwxyz1234567890";
StringBuffer sb = new StringBuffer();

for(int i=0; i<3; i++) {
sb.append(str.charAt(new Random().nextInt(str.length())));
}

return sb.toString();
}

}

class T2 implements Runnable {
private Semaphore available;
private String[]  dataStr;

public T2(){}

public T2(Semaphore available, String[]  dataStr) {
this.available = available;
this.dataStr = dataStr;
}

@Override
public void run() {
try {
this.available.acquire();
for(int i=0; i<dataStr.length; i++) {
System.out.println(this.getClass().getSimpleName() + "****" + Arrays.asList(dataStr));
}
} catch (InterruptedException e) {
e.printStackTrace();
} finally {
this.available.release();
}
}

}
不知道写的有没有啥问题 若是用condition 和 retrantlock的话 那就不需要用信号量了啊 

2012年8月24日 13:49
0 0

领导非要用信号量 semaphore来做,这种事情。。。
信号量有什么好处啊,信号量这么宽松的一个同步器,里面的permits可以任意增加减少的,你用一个线程定期release,一个线程到了5个release,还得考虑多线程的问题; 相对其他同步方式,没有好处,还带来问题,何必呢。

2012年8月24日 13:07
0 0

提醒一下,我这里因为使用了JMS的API,不是根据时间判断的
if (batch.size() == batchNum || attemptCount == 10)
attemptCount == 10,这里是JMS侦听了10次,每次间隔1S。
你如果要处理的话,可以把这个判断做成一个Function,记录每次重置List容器的厨师时间和当前时间的一个差值,以此为判断依据。

2012年8月24日 10:29
0 0

我前面做过这样一个需求,从一个队列不断地接收消息,当消息数量达到一定的数量的时候进行批量入库。当消息没有达到这个数量的时候,如果间隔时间达到一定的时间也会进行入库操作。接收消息的线程会不断地创建一个List容器,存放接收到的消息。当List达到一个阀值的时候,提交给另一个线程入库。当List没有达到这个阀值,但是连续10s没有获取到新消息的时候,同样提交给另一个线程做批量操作,将消息缓存中缓存的消息进行处理,防止这部分消息因为没有后续消息的触发而堆积在缓存中。
实例代码,接受消息创建List的部分:
while (true) {
Object message = receiveMsg();

if (message != null){
log.debug("receive message : " + message);
batch.add(message);
}else {
attemptCount ++;
}

// 批量接受一批消息之后进行处理
// 进行批量处理的条件:1、批量处理缓存消息中的数量达到要求的数量;2、一定时间段内没有收到消息时直接触发
if (batch.size() == batchNum || attemptCount == 10) {
log.info(" ++ process batch message: " + batch.size());
// 将批量消息缓存区中的消息转换成字符串消息数组,用于后续处理
String[] tms = new String[batch.size()];
for (int i = 0; i < batch.size(); i++) {
tms[i] = transformMsg(batch.get(i));
log.debug("add message : " + tms[i]);
}
// 待处理的消息缓存中有消息的话,就通过线程池启动运行处理flow
if (tms.length > 0){
ProcessExecuteTask pet = new ProcessExecuteTask();
pet.setMessage(tms);

pet.setSequenceProcessor((SequenceProcessor) processor);

executor.doExecute(pet);
batch.clear();
}
// 处理的标志lock文件存在,表示继续处理。否则,表示需要停止运行处理。
if (!flock.exists())
break;
attemptCount = 0;
}
}

2012年8月24日 10:26
0 0

需求:
1、数组大小5
2、T2线程5秒自动同步一次(不管数组是否满)
3、数组满时,不管到不到5秒 都需要主动触发T2保存

可以使用信号量:
但需要三个线程:
1、T2在等待信号量
2、T1 生成数组数据 当生产到5时释放信号量
3、T3每隔5秒释放信号量
4、T4获取信号量之后执行完任务后再等待信号量


其实可以使用wait  notify
1、T2在wait
2、T1 生成数组数据 当生产到5时 notify
3、T3每隔5秒 notify
4、T4获取信号量之后执行完任务后再 wait

2012年8月24日 08:53

相关推荐

    信号量Semaphore了解过吗?

    信号量Semaphore,这是一个在多线程编程中至关重要的同步机制,尤其在操作系统设计和并发编程领域,它扮演着协调多个线程对共享资源访问的角色。面试中被问及但回答不出,可能会显示出对并发控制理解的不足,因此,...

    Java 信号量Semaphore的实现

    Java 信号量Semaphore的实现 Java 信号量Semaphore是Java并发编程中的一种机制,用于控制多个线程的并发执行。Semaphore的实现主要是通过计数器来实现的,每个Semaphore对象都维护着一个计数器,用于记录当前可用的...

    使用信号量(Semaphore)实现线程的同步

    信号量(Semaphore)是...信号量是解决线程同步问题的一种高效工具,通过合理的信号量控制,可以有效地避免死锁、饥饿等问题,提高系统资源的利用率。理解并正确使用信号量,对于编写高效、稳定的多线程程序至关重要。

    java并发之Semaphore信号量.md

    Semaphore是计数信号量。Semaphore管理一系列许可证。每个acquire方法阻塞,直到有一个许可证可以获得然后拿走一个许可证;每个release方法增加一个许可证,这可能会释放一个阻塞的acquire方法。然而,其实并没有...

    Java信号量Semaphore

    Semaphore  Semaphore分为单值和多值两种,前者只能被一个线程获得,...单个信号量的Semaphore对象可以实现互斥锁的功能,并且可以是由一个线程获得了“锁”,再由另一个线程释放“锁”,这可应用于死锁恢复的一些场

    java哲学家就餐问题

    Java编程中解决这个问题,通常会用到多线程和同步机制,如synchronized关键字或信号量。 在这个解决方案中,"图形界面"使得问题的展示更为直观,用户可以观察到哲学家们的行为和筷子的状态。重庆大学的学生可能会...

    JAVA多线程--信号量(Semaphore)_.docx

    JAVA多线程--信号量(Semaphore) 信号量(Semaphore)是一种多线程环境下的设施,负责协调各个线程,以保证它们能够正确、合理地使用公共资源。从概念上讲,信号量维护了一个许可集。 信号量的类型有两种:单值信号...

    Java并发编程Semaphore计数信号量详解

    Java并发编程Semaphore计数信号量详解 Java并发编程中,Semaphore(信号量)是一种高效的同步机制,允许一定数量的线程访问某个资源。在本文中,我们将详细介绍Java并发编程Semaphore计数信号量的工作原理和应用。 ...

    Java 信号量编程实践

    在Java中,`java.util.concurrent.Semaphore`类为我们提供了信号量的功能,它允许我们限制同时访问某个资源的线程数量,从而实现线程同步和资源管理。 信号量主要包含两种类型:可重用信号量(非递减信号量)和二...

    Java进程信号量机制的实验程序

    综上所述,Java进程信号量机制是解决多线程环境中资源管理和同步问题的有效工具,通过Semaphore类提供的API,开发者可以灵活地控制并发程度,避免资源过度竞争,保证程序的正确性和效率。在实际项目中,根据需求选择...

    JAVA 多线程之信号量(Semaphore)实例详解

    **JAVA 多线程之信号量Semaphore实例详解** 在Java多线程编程中,信号量Semaphore是一种非常重要的同步工具,用于控制对公共资源的访问。Semaphore类位于`java.util.concurrent`包下,它允许我们限制同时访问特定...

    async-semaphore:基于Java并发信号量的计数信号量

    基于 Java 的并发信号量的计数信号量。 安装 通过 npm 安装模块: npm install async-semaphore 快速示例 // fairness false var Semaphore = require ( 'async-semaphore' ) ; var semaphore = new Semaphore ( ...

    java同步互斥信号量问题

    在Java中,我们可以使用`java.util.concurrent.Semaphore`类来实现信号量。创建一个信号量时,可以指定初始许可证的数量。以下是一个简单的示例: ```java import java.util.concurrent.Semaphore; public class ...

    redis实现分布式锁与java信号量.zip

    总的来说,Redis分布式锁和Java信号量都是解决并发问题的有效手段,理解并掌握它们对于开发高并发、高可用的分布式系统至关重要。通过深入学习和实践,我们可以更好地应对复杂分布式环境下的挑战。

    Java中Semaphore(信号量)的使用方法

    Java中Semaphore(信号量)的使用方法 Semaphore(信号量)是一种非常重要的并发访问控制机制,它可以用来保护一个或者多个共享资源的访问。Semaphore内部维护了一个计数器,其值为可以访问的共享资源的个数。一个...

    Java编程技巧(信号量,管道)

    虽然Java标准库没有直接提供同步互斥结构,但它提供了基于对象锁的`wait()`和`notify()`方法,这使得我们可以实现Dijkstra的计数信号量概念。 信号量是一种在多线程编程中用于控制资源访问的机制。在Java中,可以...

    不死锁的哲学家问题实现 java

    在Java中,我们可以使用信号量(Semaphore)来解决不死锁的哲学家问题。信号量是一种同步原语,用于控制对共享资源的访问。在本实现中,我们将创建两个类型的信号量:一个用于表示筷子,另一个用于控制哲学家可以...

    semaphore控制多线程循序执行

    Semaphore(信号量)是一种经典的同步机制,它源自于荷兰计算机科学家Edsger W. Dijkstra提出的银行家算法。本示例中,我们将深入探讨如何使用Semaphore来控制多线程的循序执行。 Semaphore是一种计数信号量,它...

    Java中的Semaphore:深入理解与应用实践

    Semaphore 是Java并发编程中实现信号量机制的重要工具。它通过维护一个许可集来控制同时访问特定资源的线程数量,从而避免资源竞争和潜在的性能问题。通过合理使用 Semaphore,可以有效地管理多线程对共享资源的访问...

    Java多线程Semaphore工具的使用详解.rar

    Semaphore,中文可译为信号量,起源于操作系统中的同步原语,用于协调多个线程对共享资源的访问。它维护了一个计数器,该计数器表示可用许可证的数量。当线程请求许可证时,如果计数器不为零,则会减少一个并允许...

Global site tag (gtag.js) - Google Analytics