admin管理员组文章数量:1567915
std::mutex 标准库的互斥锁;CRITICAL_SECTION Windows提供的临界区;QMutex Qt提供的互斥锁封装,显然,Qt封装的效率一般不如前两者。
参照这篇文章:https://www.iteye/blog/aigo-1908084
和他的结论差不多:在旧版本编译器上(如VS2012/2013),std::mutex 比临界区更慢;在新版本编译器上(如VS2015/2017),std::mutex 的效率显著提高,特别在竞争情况下比临界区快多了。
下面是 VS2013 和 VS2017 的运行截图(x86 Release):
测试代码两份:
#include <iostream>
#include <ctime>
#include <mutex>
#include <atomic>
#include <thread>
#include <list>
#include <functional>
#include <Windows.h>
//表示被锁定的资源,每次加1
long total = 0;
//win临界区
//Windows下的Mutex和CRITICAL_SECTION,都是递归锁,
//而Linux下的pthread_mutex,默认是非递归锁
CRITICAL_SECTION critical;
//互斥锁
std::mutex mtx;
//可递归互斥锁
std::recursive_mutex r_mtx;
void run_critical(int count)
{
for (int i = 0; i < count; ++i)
{
EnterCriticalSection(&critical);
++total;
LeaveCriticalSection(&critical);
}
}
void run_mutex(int count)
{
for (int i = 0; i < count; ++i)
{
//std::lock_guard<std::mutex> guard(mtx);
mtx.lock();
++total;
mtx.unlock();
}
}
void run_recursive_mutex(int count)
{
for (int i = 0; i < count; ++i)
{
//std::lock_guard<std::recursive_mutex> guard(r_mtx);
r_mtx.lock();
++total;
r_mtx.unlock();
}
}
void run_test(std::function<void()> func, int thread_count, const char * type)
{
std::list<std::thread*> threadlist;
total = 0;
clock_t start = clock();
for (int i = 0; i < thread_count; ++i)
{
std::thread *t1 = new std::thread(func);
threadlist.push_back(t1);
}
for (std::list<std::thread*>::const_iterator i = threadlist.begin(); i != threadlist.end(); i++)
{
(*i)->join();
}
clock_t finish = clock();
std::cout << std::endl << type;
std::cout << std::endl << "thread count:" << thread_count;
std::cout << std::endl << "run count:" << total;
std::cout << std::endl << "ms elapsed:" << finish - start << std::endl;
for (std::list<std::thread*>::const_iterator i = threadlist.begin(); i != threadlist.end(); i++)
{
delete(*i);
}
}
int main(int argc, char* argv[])
{
InitializeCriticalSection(&critical);
const int thread_count = 4;
const int loop_count = 1000000;
run_test(std::bind(&run_critical, loop_count), thread_count, "CRITICAL_SECTION");
run_test(std::bind(&run_mutex, loop_count), thread_count, "std::mutex");
run_test(std::bind(&run_recursive_mutex, loop_count), thread_count, "std::recursive_mutex");
DeleteCriticalSection(&critical);
system("pause");
return 0;
}
#include <QCoreApplication>
#include <QMutex>
#include <QReadWriteLock>
#include <QDebug>
#include <ctime>
#include <mutex>
#include <atomic>
#include <thread>
#include <list>
#include <functional>
#include <Windows.h>
//表示被锁定的资源,每次加1
long total = 0;
//win临界区
//Windows下的Mutex和CRITICAL_SECTION,都是递归锁,
//而Linux下的pthread_mutex,默认是非递归锁
CRITICAL_SECTION critical;
//互斥锁
std::mutex mtx;
//可递归互斥锁
std::recursive_mutex r_mtx;
//qt互斥锁
QMutex qtx{ QMutex::NonRecursive };//默认就是非递归
//qt可递归互斥锁
QMutex r_qtx{ QMutex::Recursive };
//qt读写锁
QReadWriteLock qrw{ QReadWriteLock::NonRecursive };//默认就是非递归
void run_critical(int count)
{
for (int i = 0; i < count; ++i)
{
EnterCriticalSection(&critical);
++total;
LeaveCriticalSection(&critical);
}
}
void run_mutex(int count)
{
for (int i = 0; i < count; ++i)
{
//std::lock_guard<std::mutex> guard(mtx);
mtx.lock();
++total;
mtx.unlock();
}
}
void run_recursive_mutex(int count)
{
for (int i = 0; i < count; ++i)
{
//std::lock_guard<std::recursive_mutex> guard(r_mtx);
r_mtx.lock();
++total;
r_mtx.unlock();
}
}
void run_qmutex(int count)
{
for (int i = 0; i < count; ++i)
{
qtx.lock();
++total;
qtx.unlock();
}
}
void run_recursive_qmutex(int count)
{
for (int i = 0; i < count; ++i)
{
r_qtx.lock();
++total;
r_qtx.unlock();
}
}
void run_qreadwritelock_write(int count)
{
for (int i = 0; i < count; ++i)
{
qrw.lockForWrite();
++total;
qrw.unlock();
}
}
void run_qreadwritelock_read(int count)
{
for (int i = 0; i < count; ++i)
{
qrw.lockForRead();
++total;
qrw.unlock();
}
}
void run_test(std::function<void()> func, int thread_count, const char * type)
{
std::list<std::thread*> threadlist;
total = 0;
clock_t start = clock();
for (int i = 0; i < thread_count; ++i)
{
std::thread *t1 = new std::thread(func);
threadlist.push_back(t1);
}
for (std::list<std::thread*>::const_iterator i = threadlist.begin(); i != threadlist.end(); i++)
{
(*i)->join();
}
clock_t finish = clock();
qDebug() << "\n"<< type;
qDebug() << "thread count:" << thread_count;
qDebug() << "run count:" << total;
qDebug() << "ms elapsed:" << finish - start;
for (std::list<std::thread*>::const_iterator i = threadlist.begin(); i != threadlist.end(); i++)
{
delete(*i);
}
}
int main(int argc, char* argv[])
{
QCoreApplication app(argc, argv);
InitializeCriticalSection(&critical);
const int thread_count = 4;
const int loop_count = 1000000;
run_test(std::bind(&run_critical, loop_count), thread_count, "CRITICAL_SECTION");
run_test(std::bind(&run_mutex, loop_count), thread_count, "std::mutex");
run_test(std::bind(&run_recursive_mutex, loop_count), thread_count, "std::recursive_mutex");
run_test(std::bind(&run_qmutex, loop_count), thread_count, "QMutex");
run_test(std::bind(&run_recursive_qmutex, loop_count), thread_count, "QMutex(recursive)");
run_test(std::bind(&run_qreadwritelock_write, loop_count), thread_count, "QReadWriteLock(write)");
run_test(std::bind(&run_qreadwritelock_read, loop_count), thread_count, "QReadWriteLock(read)");
DeleteCriticalSection(&critical);
return app.exec();
}
版权声明:本文标题:测试 std::mutex && CRITICAL_SECTION && QMutex 三者的效率 内容由热心网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:https://www.elefans.com/xitong/1726269042a1063590.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论