Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
cosmicing
Prj-Cpps
提交
52f3be80
P
Prj-Cpps
项目概览
cosmicing
/
Prj-Cpps
通知
2
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
P
Prj-Cpps
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
前往新版Gitcode,体验更适合开发者的 AI 搜索 >>
提交
52f3be80
编写于
10月 31, 2022
作者:
cosmicing
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
更新00-ProgramElement/1-NolockQueue/doc/无锁队列使用说明.txt
上级
86bf5dfa
变更
1
隐藏空白更改
内联
并排
Showing
1 changed file
with
113 addition
and
0 deletion
+113
-0
00-ProgramElement/1-NolockQueue/doc/无锁队列使用说明.txt
00-ProgramElement/1-NolockQueue/doc/无锁队列使用说明.txt
+113
-0
未找到文件。
00-ProgramElement/1-NolockQueue/doc/无锁队列使用说明.txt
0 → 100644
浏览文件 @
52f3be80
无锁队列使用说明
概述
无锁队列是一个线程安全的队列,采用CAS实现,支持多生产者、多消费者的场景。但是,在单生产者的场景中效率要高些。
无锁队列仅包含一个头文件。引用这个头文件即可使用。
它是一个模板类。定义在命名空间add中。有两个模板参数,第一个模板参数指定了队列中将存元素的类型。第二个模板元素指定了队列的容量:
namespace add {
template <typename T, size_t cap>
class LockFreeQueue final {
};
} // namespace
使用方式:
#include "lock_free_queue.hpp"
// 定义一个无锁队列
add::LockFreeQueue<T, 50> q;
// 入队:
T t1;
status = q.push(t1);
// 以status判断成功与否,若成功,t1已经入队。若否,说明队列满。
// 出队:
T t2;
status = q.pop(t2);
// 以status判断成功与否,若成功,t2里就是取出的值。若否,说明队列空。
成员方法
方法 参数 返回值 作用
构造函数 无 不适用 构造一个LockFreeQueue<T, cap>对象
析构函数 无 无 销毁LockFreeQueue<T, cap>对象
push const T& elem bool 将一个数据放入队列尾,若成功则返回true
push T&& elem bool 将一个数据放入队列尾(移动方式),若成功则返回true,且elem中的内容被“移动”
pop T& elem bool 从队列头移除一个元素,如果成功,返回true,且移除的元素放到elem
capacity 无 size_t 返回队列容量。由LockFreeQueue<T, cap>中的cap指定容量。
size 无 size_t 返回实际的元素数目
empty 无 bool 队列空则返回true,否则false
full 无 bool 队列满则返回true,否则返回false
约束:
约束(1): T必须能够默认构造。
约束(2): T必须满足可复制赋值 (CopyAssignable) 和可复制构造 (CopyConstructible) 的要求。
约束(3): n必需大于0。
示例
#include "lock_free_queue.hpp"
#include <chrono>
#include <string>
#include <cstdio>
using namespace std;
struct Message {
int id;
int type;
string notify;
};
int main()
{
add::LockFreeQueue<Message, 30> q;
auto product_func = [&q]() {
int id = 0;
while (id < 100) {
Message e = { id, 0, "" };
switch(id % 3) {
case 0:
e.type = 0;
e.notify = "message type 0";
break;
case 1:
e.type = 1;
e.notify = "message type 1";
break;
case 2:
e.type = 2;
e.notify = "message type 2";
break;
}
if (!q.push(e)) {
std::this_thread::sleep_for(std::chrono::microseconds(1));
continue;
}
id++;
}
};
auto consume_func = [&q]() {
int i = 0;
while (i < 100) {
Message e;
if (!q.pop(e)) {
std::this_thread::sleep_for(std::chrono::microseconds(1));
continue;
}
printf("message[%d]: type:%d, content:%s\n", e.id, e.type, e.notify.c_str());
i++;
}
};
// 生产者
std::thread p1(product_func);
std::thread p2(product_func);
// 消费者
std::thread c1 (consume_func);
std::thread c2 (consume_func);
p1.join();
p2.join();
c1.join();
c2.join();
return 0;
}
以上程序模仿两个生产者,两个消费者的程序。生产者向队列插入消息,消费者从队列取出消息。
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录