问题标签 [data-race]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
multithreading - 在并发编程的上下文中,“数据竞争”和“竞争条件”实际上是一回事吗
我经常发现这些术语在并发编程的上下文中使用。它们是相同的还是不同的?
c++ - 这个并行循环会导致数据竞争吗?
我std::vector
在并行循环之前填充了std::pair<Object, bool>
. 布尔值都初始化为true
. 循环大致如下:
由于我们只是将布尔值设置为false
我不认为这会导致数据竞争,但我不相信我对多线程的直觉。之后对该布尔结果进行的操作在单个线程中完成(bool == true
使用标准算法擦除向量中的所有元素。
这里的建议将不胜感激。我打算使用std::atomics
,但当然,它们不能用于 a ,std::vector
因为它们不是可复制构造的。
干杯!
c++ - 尝试同步队列时发生段错误
我正在学习多线程,我想模拟生产者 - 消费者问题(如果我可以称之为信号量,则使用信号量)。
我有一个包含队列的类,生产者将整数推送到队列中,消费者检索并打印它。我模拟如下
我使用了一个小控制台应用程序来调用数据:
因此,当用户输入 1 时,会将数据推送到队列中,如果用户按下 2,则会产生线程。
以任何调用它的顺序,例如,按 1 1 然后按 2,或 2 1 1 它会引发段错误。我不确定为什么我对代码的理解如下:让我们假设 order 2 1 1
我初始化了 5 个线程,他们看到队列是空的,所以他们去睡觉了。当我将一个数字推送到队列时,它会通知所有正在休眠的线程。第一个再次唤醒锁定互斥锁并继续从队列中检索数字然后释放互斥锁,当互斥锁被释放时,另一个线程执行相同操作并解锁互斥锁,互斥锁解锁后的第三个线程仍在循环中,看到队列再次为空并再次进入睡眠状态,与所有剩余线程相同。
这个逻辑正确吗?如果是这样,为什么这会一直抛出段错误,如果不是,我感谢所有解释。
谢谢您的帮助!
//edit 通过回答建议,我将 [] 替换为 vector.push_back ,但消费者现在对数据不做任何事情,不接受或打印它。
multithreading - 单写-单读大内存缓冲区共享无锁
假设我有一个用作帧缓冲区的大内存缓冲区,它由一个线程(甚至多个线程,保证没有两个线程同时写入相同的字节)不断写入。这些写入在时间上是不确定的,分散在代码库中,并且无法被阻止。
我有另一个单线程定期读取(复制)整个缓冲区以生成显示帧。这个读取也不应该被阻止。就我而言,撕裂不是问题。换句话说,我唯一的目标是写入线程所做的每一个更改最终都应该出现在读取线程中。排序或一些(与显示刷新率相比可以忽略不计)延迟无关紧要。
同时读取和写入相同的内存位置是一种数据竞争,这会导致 c++11 中的未定义行为,本文列出了相同的非常可怕的示例,其中优化编译器生成的内存读取代码会改变数据竞争的存在。
不过,我需要一些解决方案,而无需完全重新设计此遗留代码。从实际的角度来看,每条建议都会考虑什么是安全的,而不管它在理论上是否正确。我也对非完全便携的解决方案持开放态度。
除此之外,我有一个数据竞争,我可以通过在线程之间建立同步关系(获取-释放一个原子保护变量,仅用于其他目的)或通过将特定于平台的内存栅栏调用添加到编写器线程中的关键点。
我针对数据竞赛的想法:
使用组件作为阅读线程。我会尽量避免这种情况。
使内存缓冲区易失,从而防止编译器优化参考文章中描述的这些讨厌的东西。
将读取线程的代码放在单独的编译单元中,用-O0编译
+1。保持一切原样,交叉手指(因为目前我没有注意到问题):)
上面列表中最安全的是什么?你看到更好的解决方案了吗?
仅供参考,目标平台是 ARM(多核)和 x86(用于测试)。
(这个问题将前一个问题具体化,这有点太笼统了。)
c++ - std::vector::clear()-ing 二维向量线程的内部向量是否安全?
假设我有一个threadWork
初始化为的对象:
然后我部署线程,每个线程都通过sN_THREADS
执行写入到.vector::push_back()
vector<myType>
threadWork
然后一个线程调用vector::clear()
它的元素threadWork
。这是否会使其他线程对其元素的写入无效?即可以vector::clear()
调用一个元素来threadWork
改变其他元素的内存分配threadWork
,从而导致线程可能写入无效地址?
go - 使用 golang 避免数据竞赛工作者
我有一个 jobWorker 应该处理工作,并且在这个工作人员中有数据库读写、日志文件、接收 api 和一些数据计算。
这是我运行 go-worker 的主要功能。
数据竞争问题让工作人员使用的日志和我的数据混淆了。任何方式都可以简单地解决没有锁(Mutex.Lock)的数据竞争问题。我希望工作可以更快地由工人处理。
任何建议或提示都会有所帮助。谢谢。
c++ - 允许这种编译器转换吗?
考虑这段代码,其中x
和y
是整数:
是否允许以下编译器转换?
上下文:
这是来自 Bjarne Stroustrup 的常见问题解答:
常见问题解答指出这是免费的数据竞赛;和x
两者y
都为 0,则不应写入任何变量。
但是如果允许转换呢?
go - 为什么这段代码会导致数据竞争?
我用这段代码运行命令go run --race
并得到:
m1
并且m2
是不同的变量,为什么第 16 行和第 11 行会导致数据竞争?
我的 Go 版本是 1.8。我想这是一些编译优化,有人可以告诉我吗?非常感谢。
swift - 解决 iOS Swift 中的数据竞争
我有 NetworkProvider,它将不断地调用 api,并且一旦我收到数据,我将更新用户 ID。同时,我将从其他功能访问用户 ID。
这是数据竞争条件,有人可以帮助删除条件。
`
go - 使用 slack bot 处理多个数据竞争
作为我的第一个 golang 项目,我正在开发一个 slack bot,虽然这个特定的 bot 命令的功能很好,但它可能会随机恐慌并引发错误。
我能够确定我正在进行数据竞赛,特别是我的两个 go 例程。但是我很难确定如何修补它们,或者做互斥锁是否是处理共享变量的正确方法。
我试图弄清楚问题是我的结果变量,它被分成通道,每个通道都由 go 例程处理,或者它是我的缓冲区变量,os.exec 包使用它来运行两个标准输出的命令和 stderr 修改。
这是下面的代码和数据竞争示例。
数据竞赛: