我想我误解了FileChannel的锁定功能是如何工作的.
我想对文件进行独占写锁定,但允许从任何进程读取.
在运行Java 7的Windows 7计算机上,我可以使FileChannel的锁定工作,但它会阻止来自其他进程的读取和写入.
如何实现不允许写入但允许其他进程读取的文件锁?
我知道可以boost::UpgradeLockable
在 C++14 中使用。
C++11 有类似的东西吗?
我有一些数据结构,我想在其中独占锁定写入访问,但启用并行读取访问。
我进行了一些搜索,找到了类ReadWriteLock
和ReentrantReadWriteLock
- 它们都提供读锁和写锁。
我不明白它们之间有什么区别。有人可以解释一下吗?
我有一个互斥体库,并且正在尝试实现一个写优先锁。我正在看这个例子:
https://en.wikipedia.org/wiki/Readers%E2%80%93writer_lock
我了解读优先锁,但不了解写优先锁。有人可以解释如何实施吗?
具体来说,我不明白这部分:
While w:
wait c, m
Run Code Online (Sandbox Code Playgroud)
我也不明白该标志是否w
是通用的,或者只是每个进程有一个不同的标志。我认为是前者。
例如,这里我们看到获取读锁的算法:
Lock m (blocking).
While (w or r > 0):
wait c, m
Set w to true.
Unlock m.
Run Code Online (Sandbox Code Playgroud)
但这是什么wait c, m
意思呢?c
这并不意味着等待同时获得和 的锁定m
,因为我们已经m
在步骤 1 中锁定了。
而且, for Set w to true
- 这是否意味着w
必须在所有进程中或仅在这个进程中设置为 true ?
我试图证明当有许多读者和只有一些作者时,synchronized会变慢.不知怎的,我证明了相反.
RW示例,执行时间为313 ms:
package zad3readWriteLockPerformance;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReadWriteLock;
import java.util.concurrent.locks.ReentrantReadWriteLock;
public class Main {
public static long start, end;
public static void main(String[] args) {
Runtime.getRuntime().addShutdownHook(new Thread(() -> {
end = System.currentTimeMillis();
System.out.println("Time of execution " + (end - start) + " ms");
}));
start = System.currentTimeMillis();
final int NUMBER_OF_THREADS = 1000;
ThreadSafeArrayList<Integer> threadSafeArrayList = new ThreadSafeArrayList<>();
ArrayList<Thread> consumerThreadList = new ArrayList<Thread>();
for (int i = 0; i < NUMBER_OF_THREADS; i++) {
Thread …
Run Code Online (Sandbox Code Playgroud) 我读到写锁是独占的,而读锁是共享的,因此无论如何都可以通过多个线程访问处于读锁中的一段代码。如果争用线程没有获取读锁怎么办。无论如何,他们将只阅读。另外,如果获取读锁的线程尝试写一些东西怎么办?
谢谢
考虑以下JDK
标准接口:
public interface ReadWriteLock{
public Lock readLock();
public Lock writeLock();
}
Run Code Online (Sandbox Code Playgroud)
B. Goetz在Java Concurrency中实际上提到从readLock升级到writeLock容易死锁。
如果两个读取器同时尝试升级到写入锁,则任何一个都不会重新获得读取锁。
让我感到困惑的是,有两个读者试图升级。但是,即使一个读者也足够了,不是吗?如果读取器尝试升级,则不会释放读取锁。试图在持有读锁定的情况下获取写锁定是死锁的。
因此,从这一点来看,我认为提供升级操作在理论上甚至都是荒谬的。也许实现可以解决这个问题?
** 这是针对大学课程的,我实际上并不是在尝试破解密码 ** 下面是我的源代码,但基本上我想要发生的是父进程将密码排入 std::list<> 尝试列表。然后子线程从队列的前面抓取,目前只打印出值。
正如您在下面的代码中看到的那样,我尝试使用 std::mutex 在弹出前端时阻止尝试列表,但是两个线程同时吹过锁并从前端读取。然后其中之一出现分段错误并且程序崩溃。
seg faulting 的具体代码部分是...
mutex.lock();
password = attemptList.front();
attemptList.pop_front();
size = attemptList.size();
std::cout << password << std::endl;
mutex.unlock();
Run Code Online (Sandbox Code Playgroud)
#include <cmath>
#include <cstdlib>
#include <cstring>
#include <string>
#include <iostream>
#include <chrono>
#include <shared_mutex>
#include <unistd.h>
#include <sys/ipc.h>
#include <mutex>
#include <sys/shm.h>
#include <sys/wait.h>
#include <thread>
#include <vector>
#include <algorithm>
#include <list>
#define MAX_LENGTH 4
#define MAX_QUEUE_SIZE 1000
#define CHARACTER_LIST "abcdefghijklmnopqrstuvwxyz"
void enqueue_passwords(const std::string& charList);
void bruteforce();
void do_join(std::thread& t);
void join_all(std::vector<std::thread>& v);
std::list<std::string> …
Run Code Online (Sandbox Code Playgroud) 什么是允许从列表(或其他数据结构)上的多个线程进行搜索的好方法,但是阻止对列表进行搜索并对不同线程上的列表进行编辑以进行交错?我尝试在搜索和编辑方法中使用synchronized块,但是当尝试在多个线程中运行搜索时,这会导致不必要的阻塞.
编辑:ReadWriteLock正是我想要的!谢谢.
我想就此解决一个小纠纷.任何帮助将不胜感激.
我编写了自己的文件处理程序,它附加到记录器.这是一个文件处理程序,并由多个线程访问,我使用同步,以确保在写入过程中没有冲突.此外,它是一个滚动日志,所以我也关闭并打开文件,也不希望有任何问题.
他对此的回应是(从电子邮件中粘贴)
我坚信Handler中的同步非常糟糕.这么简单的任务太复杂了.所以,我想说为什么不为每个线程使用一个实例?
从性能和内存管理的角度来看,你会说什么更好.非常感谢您的回复.每当在多线程应用程序中涉及写入和读取时,我一直在Java应用程序上使用同步,并且没有听说过任何严重的性能问题.
所以,我想知道是否有任何问题,我真的应该切换到每个线程一个实例.
一般来说,使用同步的垮台是什么?
编辑:我之所以编写自定义文件处理程序(是的,我喜欢slf4j),是因为我的自定义处理程序一次处理两个文件,另外我还有很少的其他函数在写入文件时执行.
我编写了一个Java ReadWriteLock,读者使用双重检查锁定来获取写锁定.这是不安全的(对于具有延迟实例化的DCL的情况)?
import java.util.concurrent.atomic.AtomicInteger;
public class DCLRWLock {
private boolean readerAcquiringWriteLock = false;
private boolean writerLock = false;
private AtomicInteger numReaders = new AtomicInteger();
public void readerAcquire() throws InterruptedException {
while (!nzAndIncrement(numReaders)) {
synchronized (this) {
if (numReaders.get() != 0)
continue;
if (readerAcquiringWriteLock) {
do {
wait();
} while (readerAcquiringWriteLock);
} else {
readerAcquiringWriteLock = true;
writerAcquire();
readerAcquiringWriteLock = false;
assert numReaders.get() == 0;
numReaders.set(1);
notifyAll();
break;
}
}
}
}
public void readerRelease() {
if (numReaders.decrementAndGet() == 0)
writerRelease(); …
Run Code Online (Sandbox Code Playgroud) java atomic thread-safety readwritelock double-checked-locking
我正在做一个我们使用Cassandra的项目,而且我已经陷入了优化点.我们想要改变数据库结构,因为读取操作对Cassandra来说是一个相当大的负载.
我搜索了文档和论坛的答案,但我找不到下面问题的明确答案.
目前我们小批量写入Cassandra,阅读将不断发生.我们希望使批次更大,所以我们可能每10-15分钟左右改变一半.据我所知,Cassandra只在应用写入操作时锁定行.但这是真的吗?或者在写入时锁定整个表格.并且(可能有点愚蠢的问题)你可以在有写锁时阅读吗?(因为当只有一个写锁定权时你有可能仍然可以阅读吗?).
文档没有显示这种流程,这个问题似乎从未被问过.提前致谢!
当我学习shared_mutex
C++17时,我发现一个奇怪的问题。如果我在一个线程中调用两次,然后在另一个线程中shared_lock
调用,那么我的程序将冻结。unique_lock
像这样:
std::mutex mutex;
std::shared_mutex s_mutex;
int i = 0;
void func() {
auto lock = std::shared_lock(s_mutex);
auto lock1 = std::shared_lock(s_mutex);
++i;
}
void func2() {
auto lock = std::unique_lock(s_mutex);
++i;
}
int main() {
auto t1 = std::thread([](){
auto i = 10000;
while(i--) {
func();
}
});
auto t2 = std::thread([](){
auto i = 10000;
while(i--) {
func2();
}
});
t2.join();
t1.join();
std::cout << i << std::endl;
return 0;
}
Run Code Online (Sandbox Code Playgroud)
这个问题好像只出现在windows上,我在Arch linux上尝试过,效果很好。
我在用着g++.exe …
readwritelock ×13
java ×8
c++ ×3
locking ×3
mutex ×2
atomic ×1
c++11 ×1
cassandra ×1
deadlock ×1
performance ×1
rwlock ×1
synchronized ×1
windows ×1