std::thread创建线程,使用std::ref()传递类对象参数

std::ref用法以及和&引用区别 阅读详情

问题描述

一个小的知识点,因为对std:thread不熟悉,刚才写代码出现了一个问题。

void test1(ThreadSafeListTest& tslt)
{
    while (true)
    {
        tslt.thread_safe_list_test1();
    }
}



ThreadSafeListTest test;
std::thread t1(test1, test);  // 这样写,报错

在这里插入图片描述

解决方案

使用 std::ref()即可。

std::thread t1(test1, std::ref(test));

原因是:
thread在使用类对象作为参数传递过程中,常常会出现多次拷贝构造的情况,理想中的情况是只需一次拷贝构造。原因是由于不同编译器对thread函数处理是不同的。

std::ref()详解

参考资料

std::ref只是尝试模拟引用传递,并不能真正变成引用,在非模板情况下,std::ref根本没法实现引用传递,只有模板自动推导类型时,ref能用包装类型reference_wrapper来代替原本会被识别的值类型,而reference_wrapper能隐式转换为被引用的值的引用类型。

  • List item

bind

std::ref主要是考虑函数式编程(如std::bind)在使用时,是对参数直接拷贝,而不是引用。

  • thread

其中代表的例子是thread
比如thread的方法传递引用的时候,必须外层用ref来进行引用传递,否则就是浅拷贝。

C++ thread线程函数传参原理剖析 通过C++ Thread类库源码剖析thread线程函数传参原理 阅读详情

相关推荐

C++编程法则365天一天一条(302)std::ref引用包装器

std::ref和std::cref在函数式编程中的作用是非常大的,C++标准库中多次使用到了它们。而std::ref和std::cref事实上是模板函数,返回值是一个std::reference_wrapper对象,而std::reference_wrapper虽然是一个对象,可是他却能展现出和普通引用类似的效果,这点和前一篇文章讲的智能指针如出一辙(事实上标准库大多是这样设计的,这也是运算符重载存在的一个重要意义)。

二进制君 6391

解析C++中std::ref

1. 前言 关于c++中的std::ref,std::ref在c++11引入。本文通过讲解std::ref的常用方式,及剖析下std::ref内部实现,进而再来讲解下std::reference_wrapper,然后我们再进一步分析为什么使用std::ref。 2. std::ref 用法 简单举例来说: int n1 = 0; auto n2 = std::ref(n1); n2++; n1++; std::cout << n1 << std::endl; // 2 std:

leapmotion的博客 1万+

C++笔记之std::move ,std::ref,std::bind

本文简要学习记录。 1、std::move 使用场景如下: (1)c++标准库使用比如vector::push_back等这类函数时,会对参数的对象进行复制,连数据也会复制。这就造成了对象内存的额外创建,本来原意是想把参数push_back进去就可以了。 (2)c++11提供了std::move函数来把左值转换为xrvalue,而且新版的push_back也支持&&参数的重载版本,这时候就可以高效率地使用内存了。 使用前提: (1)定义的类使用了资源并且定义了移动构造函数和移

deep_love1314的博客 1875

c++11 为什么使用ref,和引用的区别

std::ref只是尝试模拟引用传递,并不能真正变成引用,在非模板情况下,std::ref根本没法实现引用传递,只有模板自动推导类型时,ref能用包装类型reference_wrapper来代替原本会被识别的值类型,而reference_wrapper能隐式转换为被引用的值的引用类型。 std::ref主要是考虑函数式编程(如std::bind)在使用时,是对参数直接拷贝,而不是引用 ...

weixin_30695195的博客 367

Halcon手眼标定实战:从九点标定到机械臂精准抓取(附完整代码)

本文详细介绍了Halcon手眼标定技术在实际工业场景中的应用,重点讲解了九点标定法在机械臂精准抓取中的实现步骤和优化技巧。通过对比Eye-to-Hand和Eye-in-Hand两种模式的特点,提供完整的代码示例和误差分析,帮助工程师快速掌握标定技术,提升自动化系统的精度和稳定性。

weixin_29100927的博客 460

Android wifi源码分析(二) Wifi关闭流程

接着上一篇,这篇说一下Wifi的关闭流程。 由上一篇可以知道,framework层提供的wifi开关接口都是**setWifiEnabled**,只是参数不同而已。*true*表示开启wifi、*false*表示关闭wifi。

奋斗的菜鸟ing 3300

C++多线程编程

创建线程的方法 头文件 #include 线程函数 类对象 线程传递参数 相关函数 mythread.join():阻塞主线程,等待子线程执行完毕; mythread.detach():将子线程与主线程分离,主线程不再等待子线程 std::ref():若要使用引用来改变原来参数,就用std::ref() std::move():并不能移动任何东西,它唯一的功能是将一个左值强制转化为右值...

qq_43749617的博客 172

PLC与变频器联动控制:从开关量、模拟量到通讯的接线与编程实战

在工业自动化系统中,电机调速控制是核心需求之一,其关键在于实现可编程逻辑控制器(PLC)与变频器之间的可靠联动。其基本原理是通过PLC输出控制信号,由变频器接收并驱动电机按设定速度运行。这项技术的核心价值在于实现电机的软启停、精确调速与节能控制,广泛应用于风机、水泵、传送带及精密张力控制等场景。其中,开关量控制以其接线简单、抗干扰能力强的特点,成为基础且可靠的方案;而模拟量控制则能实现无级平滑调速,满足更高精度的工艺要求。本文以西门子、三菱等主流品牌为例,深入解析了这两种主流控制方式的硬件接线、参数设置与梯

1270

C++11 多线程(std::thread)详解

本文介绍了C++11标准库中的std::thread多线程编程基础。

jcShan709的博客 15万+

ZYNQ microblaze boot.bin固化步骤

一,ZYNQ移植软核的原理FPGA规模巨大而且功能复杂,因此设计的每一个部分都从头开始是不切实际的。一种解决的办法是:对于较为通用的部分可以重用现有的功能模块,而把主要的时间和资源用在设计中的那些全新的、独特的部分。这就像是你在开发应用程序的时候就不用直接去写驱动物理硬件的代码,而是直接调用Windows提供的API就行了。

wangjie36的博客 2782

2024-12月js逆向案例-sensor-data之vmp字段之akamai_2/3.0-(下)

akamai2/3的vmp字段逆向分析

十一姐的博客 3147

C++11 thread 参数传递深度解析:为什么需要 std::ref 而非直接引用?

摘要:C++11的std::thread在参数传递时默认采用值拷贝方式,即使线程函数声明为引用参数。这种设计避免了多线程中的悬空引用问题,但也导致无法通过引用修改原始变量或传递不可拷贝对象。std::ref/cref提供解决方案,它们包装引用使其按引用传递,同时在语法上明确标识出潜在的共享数据。本文通过代码示例展示了直接传递引用的陷阱,并解释std::ref如何保留引用语义,同时提醒开发者注意线程安全。

Lion_Long的博客 1916

手把手教你学PCIE(9.3)--pcie常见故障及原因:配置错误介绍

PCIe 设备的配置错误可能涉及操作系统设置、BIOS 设置、驱动程序设置和配置文件设置等多个方面。通过以上方法,可以有效地诊断和解决 PCIe 设备的配置错误。

MHD0815的博客 2440

C++ 多线程(3)std::thread 详解

文章目录一、头文件二、std::thread 构造函数三、其他成员函数四、传递临时参数作为线程对象的注意事项4.1 **解决办法:**4.2 原因分析4.3 总结五、传递类对象、智能指针作为线程参数5.1 修改子线程中的对象,不会影响主线程中的对象5.2 传递智能指针参考链接: 一、头文件 std::thread 在 头文件中声明,因此使用 std::thread 时需要包含 头文件。 二、std::thread 构造函数 (1). 默认构造函数,创建一个空的 thread 执行对象。 (2). 初始

一抹烟霞的博客 1万+

【异常】Cursor 模型服务地域访问限制报错的完整排查与解决方案This model provider doesn‘t serve your region

其本质是:Cursor客户端依赖的上游大语言模型服务提供商,基于自身服务的合规运营范围,对客户端发起的请求进行了来源地域权限校验;当系统检测到请求的网络来源地域,不在该模型服务商官方授权提供服务的地域范围内时,会触发服务访问拦截策略,拒绝响应本次模型调用请求,最终在客户端抛出该报错。合规声明:本文所提供的所有方案,均仅用于技术问题排查与解决,请您在使用过程中严格遵守当地法律法规,以及对应软件与模型服务提供商的用户协议与合规要求。更多关于AI+教育领域的干货,可以关注我的微信公众号一时间获取哦~

奶爸的编程之路,也就一周冷个三天 1134

ATECC508A芯片开发笔记(四):自定义配置508功能,规划DataZone数据存储

ATECC508A芯片开发笔记(四):自定义配置508功能,规划DataZone数据存储 508A内部存储区介绍 Data Zone Config Zone 508A Config Zone配置(自定义) - ATECC508A芯片在使用之前,需要自定义配置ConfigZone与DataZone,并同Lock命令将两个区域锁住,否则无法正常使用功能。而一旦锁上就是永久性的,配置区不能够进行解锁

HowieXue 薛永浩的博客 2万+

C++-std::thread之向线程函数传递参数

文章目录向线程函数传递参数 向线程函数传递参数 向线程函数传递参数只需要向std::thread构造函数传递额外的参数即可 std::thread t(hello,arg1,arg2); 需要注意的是,参数会被拷贝到单独的存储空间中,然后作为右值传递给可调用对象。 void f(int i,std::string const& s); std::thread t(f,3,"hello"); 这里"hello"作为const char *传递给构造函数,并且只在新线程的上下文中转换为string类

mrbone11的博客 9657

jre9下载 jdk9

(Java SE Runtime Environment 9.0) 9.0u175 官方最新版 【x86|x64】

C++11 std::ref实战指南:如何在std::bind和std::thread中正确传递引用

本文深入解析C++11中std::ref的核心机制与实战应用,重点指导如何在std::bind和std::thread中正确传递引用。通过剖析值语义导致的常见陷阱,并结合代码示例,详细阐述了使用std::reference_wrapper确保函数对象与多线程编程中引用传递有效性的方法,帮助开发者编写正确、高效的C++代码。

nept的博客 631

最新的sdio 4.0 spec 协议标准 带书签 高清完整PDF版

Part-E1-SDIO-Specification-Ver4.00-Final-120220.pdf:最新的sdio 4.0 spec 协议标准 带书签 高清完整PDF版,包括SDIO 接口的外设,SDIO 接口官方协议等。

假人有限元模型

假人模型,车辆碰撞假人有限元模型,适合做乘员安全的研究者利用

std::thread的常用参数传递总结

实参的生命周期 给std::thread传递参数的时候要注意,参数是引用或者指针的情况下,要注意生命周期的问题 #include <iostream> #include <thread> #include <chrono> #include <fstream> using namespace std::chrono_literals; void func_str(const std::string & str) { std::this_thr

惊鸿一博 3060

廖雪峰Python教程[完整版]

廖雪峰的python教程整理的,已经排好版了,而且还是完整的,适合小白

C++ std::ref————详解

想学习ref,必须先学习reference_rapper 1、是什么? ref是个函数模板: 用来构建一个reference_wrapper对象并返回,该对象拥有传入的elem变量的引用。如果参数本身是一个reference_wrapper类型的对象,则创建该对象的一个副本,并返回。 2、为什么要有ref std::ref主要在函数式编程(如std::bind)时使用,bind是对参数直接拷贝,无法传入引用(即使你传入的实参是引用类型也不行),故引入std::ref()。使用std::ref可以在模板传参

m0_51551385的博客 1万+

std::ref函数

C++11 的std::ref函数就是为了解决在线程的创建中等过程的值拷贝问题,下面将会用一个线程的创建来展示ref函数的作用。 首先我们先来写一个以类对象为参数的线程的创建,先来看一下下面的这个代码: #include <iostream> #include <thread> using namespace std; class A { pub...

Charles_Zaqdt的博客 5060

穿越线程边界的参数迷宫:std::thread参数传递的七种武器

本文深入探讨了C++11中std::thread参数传递的七种关键技术,包括std::ref引用包装器、移动语义、Lambda捕获等,帮助开发者解决线程边界参数传递的常见陷阱。通过分析底层实现原理和性能对比,为高效线程创建和安全参数传递提供了实用解决方案。

weixin_29309213的博客 630

[C++]C++11多线程thread参数传递问题

多线程在很多地方都是必须要掌握的方法,这里先说一下,thread对象的参数传递问题。

FL1768317420的博客 1457

c++_std::thread多线程

c++的thread多线程基础的学习,自查回顾看

前端开发工程师 601

C++11 std::thread 实战:5种线程创建方式与参数传递避坑指南

本文深入探讨了C++11中std::thread的5种线程创建方式与参数传递技巧,涵盖普通函数、成员函数、Lambda表达式等多种实现方法,并详细解析了引用传递、Move-only类型处理等常见陷阱。通过实战代码示例和性能优化建议,帮助开发者掌握现代C++多线程编程的核心技术,提升并发程序开发效率。

weixin_30924087的博客 343

std::thread和pthread的区别 及 传递对象指针和引用

std::thread和pthread的区别 及 传递对象指针和引用引言区别std::thread 如何传递对象 引言 朋友突然问我,pthread和std::thread有什么区别?我不知道他为什么会问到这个问题,但是看到问题后我的第一反应是,你是不是C和C++混学的。 区别 pthread是linux下的多线程API,头文件为pthread.h,关于linux线程和进程区别本篇文章略过,因为本文算是给自学人的科普。 std::thread是c++标准库中的线程库,其意义在于可以跨平台不改代码 因为在wi

Doub1's Blog 5225
上一篇: C++并发编程:线程安全链表
下一篇: 一种轻量的“虚拟机”——Windows 沙盒模式
CodeBowl
博客等级 码龄5年 7664粉丝 67原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值