Tag: 并发

并发线程同时添加到ArrayList – 会发生什么?

我们有多个线程调用ArrayList上的add(obj) 。 我的理论是,当两个线程同时调用add时,只有两个被添加的对象中的一个真的被添加到ArrayList 。 这是可信的吗? 如果是这样,你怎么解决这个问题? 使用像Vector这样的同步集合?

为什么我需要std :: condition_variable?

我发现std::condition_variable由于虚假唤醒而非常难以使用。 所以有时我需要设置一个标志,如: atomic<bool> is_ready; 我在调用notify( notify_one()或notify_all() )之前将is_ready设置为true ,然后等待: some_condition_variable.wait(some_unique_lock, [&is_ready]{ return bool(is_ready); }); 有什么理由不应该这样做:(编辑:好吧,这真是一个坏主意。) while(!is_ready) { this_thread::wait_for(some_duration); //Edit: changed from this_thread::yield(); } 如果condition_variableselect了等待时间(我不知道这是否是真的),我宁愿自己select它。

这是使用java.util.concurrent.FutureTask的好方法吗?

首先,我必须说我对API java.util.concurrent很陌生,所以也许我所做的是完全错误的。 我想做什么? 我有一个基本上运行2个独立处理(称为myFirstProcess , mySecondProcess )的Java应用程序,但是这些处理必须同时运行。 所以,我试图这样做: public void startMyApplication() { ExecutorService executor = Executors.newFixedThreadPool(2); FutureTask<Object> futureOne = new FutureTask<Object>(myFirstProcess); FutureTask<Object> futureTwo = new FutureTask<Object>(mySecondProcess); executor.execute(futureOne); executor.execute(futureTwo); while (!(futureOne.isDone() && futureTwo.isDone())) { try { // I wait until both processes are finished. Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } } logger.info("Processing finished"); executor.shutdown(); […]

SwitchToThread / Thread.Yield与Thread.Sleep(0)与Thead.Sleep(1)

我试图编写最终的“收益率”方法来产生当前时间片到其他线程。 到目前为止,我发现有几种不同的方法可以使线程产生分配的时间片。 我只是想确保我正确解释他们,因为文件不是很清楚。 所以,从我读到的stackoverflow,MSDN和各种博客文章,下面的选项存在,都有不同的优点/缺点: SwitchToThread [win32] / Thread.Yield [.NET 4 Beta 1]:产生到同一处理器上的任何线程 优点:大约是Thread.Sleep(0)两倍 缺点:只产生同一个处理器上的线程 Thread.Sleep(0) :产生任何处理器上相同或更高优先级的线程 优点:比Thread.Sleep(1)更快Thread.Sleep(1) 缺点:只产生相同或更高优先级的线程 Thread.Sleep(1) :产生任何处理器上的任何线程 优点:屈服于任何处理器上的任何线程 缺点:最慢的选项(如果不使用timeBeginPeriod / timeEndPeriod [win32], Thread.Sleep(1)通常会挂起线程大约15ms) 那么Thread.SpinWait呢? 可以用来产生线程的时间片吗? 如果不是,它用于什么? 我还有一些我错过了或错误解释的东西。 如果你能改正/补充我的理解,我将不胜感激。 这是我的Yield方法迄今为止的样子: public static class Thread { [DllImport("kernel32.dll")] static extern bool SwitchToThread(); [DllImport("winmm.dll")] internal static extern uint timeBeginPeriod(uint period); [DllImport("winmm.dll")] internal static extern uint timeEndPeriod(uint […]

如何运行并发unit testing?

如何使用junit来运行并发testing? 假设我有一堂课 public class MessageBoard { public synchronized void postMessage(String message) { …. } public void updateMessage(Long id, String message) { …. } } 我想同时testing多个访问这个postMessage。 对此有何build议? 我希望对我所有的setter函数(或涉及到创build/更新/删除操作的任何方法)运行这种并发性testing。

线性化与可串行化的区别

我对Java编程的线性化和可串行化感到困惑。 你可以用一个例子来解释这些差异吗?或者提供一个很好的参考。

并发通用数据结构,没有死锁或资源匮乏

我最近问了一些有关TVar的问题,我仍然对livelock感到担忧。 所以我想到了这个结构: 每个事务都有一个唯一的优先级(可能是按创build顺序分配的)。 事务尝试获取对其访问的数据的读/写locking。 自然地,同时读取是可以的,但是一个写入locking排除所有其他(读取和写入)。 说事务A的优先级比事务B的优先级高。如果A持有锁,B等待,但是如果B持有锁并且A需要它,则B从锁中引导,A获得它,并且事务B重新启动(如同TVar ) 。 然而B保持当前优先重试。 当一个锁被释放并且等待事务时,它将进入最高优先级的事务,其余的继续等待。 我相信这个系统可以防止死锁,但也可以防止饥饿(与TVar不同)。 我想知道是否有人实施了这样一个系统,因为它似乎相当明显,我不想重新发明轮子。 当然,这样的方法很容易扩展到允许用户指定优先级。 优先级可以是pair (user_supplied_prio, auto_increment) , user_supplied_prio优先,但优先级相同的任务按FIFO顺序parsing。 评论/解决scheme: 实际上,当我想到这一点时,Haskell中已经存在,只需要使用一个IORef包装所有的数据,并且只使用atomicModifyIORef 。 atomicModifyIORef将确保交易按顺序应用。 但是,有人可能会认为这意味着数据结构是顺序的(即有效地限于一个线程),但实际上由于懒惰而是并行的。 为了解释这一点,考虑一个昂贵的函数f 。 我们打算把这个应用到一个Data.Map的关键字“foo”的数据。 用(foo -> future(fx))replace(foo -> x) (foo -> future(fx)) 。 这个线程将继续确定(fx)实际是什么,但同时我们可以将g应用到“bar”中。 由于将g应用于“bar”并不需要“foo”的结果,因此我们可以同时处理这个问题。 没有死锁,没有饥饿,最终所有交易将被处理(大致按照他们收到的顺序)。

为什么添加并发性降低了这个golang代码?

我已经有了一些Go代码,我一直在琢磨着回答我的一个小小的好奇心,这个代码跟我的姐夫在玩的video游戏有关。 本质上,下面的代码模拟了与游戏中的怪物的交互,以及他多久可以期望他们在失败时丢弃物品。 我遇到的问题是,我期望这样的一段代码对于并行是完美的,但是当我添加并发时,所有模拟的时间往往会减慢4-6倍没有并发。 为了让你更好地理解代码是如何工作的,我有三个主要function:交互function,它是玩家和怪物之间的简单交互。 如果怪物掉落物品则返回1,否则返回0。 模拟function运行多个交互并返回一片交互结果(即1和0表示成功/不成功的交互)。 最后,有一个testing函数,它运行一系列模拟,并返回一个模拟结果片断,这个结果是导致一个丢失项目的交互总次数。 这是我试图并行运行的最后一个function。 现在,我可以理解为什么如果我为每个要运行的testing创build一个goroutine,代码就会变慢。 假设我正在运行100个testing,在我的MacBook Air的4个CPU之间的每个goroutine之间的上下文切换将会导致性能下降,但是我只创build了多个goroutines,因为我拥有处理器,并将testing次数够程。 我希望这可以加快代码的性能,因为我并行地运行了每个testing,但是,当然,我正在慢慢地减速。 我很想弄清楚为什么会这样,所以任何帮助将不胜感激。 下面是没有执行例程的常规代码: package main import ( "fmt" "math/rand" "time" ) const ( NUMBER_OF_SIMULATIONS = 1000 NUMBER_OF_INTERACTIONS = 1000000 DROP_RATE = 0.0003 ) /** * Simulates a single interaction with a monster * * Returns 1 if the monster dropped an item and 0 […]

goroutines如何工作? (或者:goroutines和OS线程关系)

其他例程在调用系统调用时如何继续执行? (使用GOMAXPROCS = 1时) 据我所知,当调用系统调用时,线程放弃控制,直到系统调用返回。 如何在不通过阻塞系统调用goroutine创build系统线程的情况下实现这种并发性? 从文档 : 够程 它们被称为goroutines,因为现有的术语(线程,协程,进程等等)传递的是不准确的内涵。 goroutine有一个简单的模型:它是一个在同一个地址空间中与其他goroutines同时执行的函数。 它是轻量级的,比堆栈空间的分配花费更多。 堆栈起点很小,所以它们很便宜,而且根据需要分配(并释放)堆存储空间以增加堆栈。 Goroutines被多路复用到多个OS线程,所以如果应该阻塞,比如在等待I / O的时候,其他的继续运行。 他们的devise隐藏了许multithreading创build和pipe理的复杂性。

如何在Clojure中启动一个线程?

关于并发性,我已经读了很多关于Clojure的优秀之处,但是我没有看到实际的教程解释了如何创build一个线程。 你只是(。开始(Thread。func)),还是有其他的方式,我已经错过了?