03C++11多线程编程之测试join,detach传各种实参时形参的拷贝次数

2023-10-29

03C++11多线程编程之测试join,detach传各种实参时形参的拷贝次数

首先我们看下面的总结测试图,然后一步步的测试。
在这里插入图片描述

1 这里我们先测试join传实参的类型
当实参为普通对象时:

1)当形参为普通对象时,拷贝了两次。
在这里插入图片描述

2)当形参为引用时:拷贝了一次。
在这里插入图片描述

3)当形参为指针时:无拷贝。
在这里插入图片描述

当实参为临时对象时:

1)形参为值时,拷贝了两次。
在这里插入图片描述
2)形参为引用时,拷贝了一次,并且在主线程拷贝构造完毕。
在这里插入图片描述
3)当形参为指针时:无拷贝。
在这里插入图片描述
当实参为引用时:

1)当形参为普通对象时:拷贝一次。
在这里插入图片描述
2)当形参为引用时:无拷贝。
在这里插入图片描述

3)当形参为指针时:无法传参。

thread mytobj(MyPrint, std::ref(a));//error
thread mytobj(MyPrint, &std::ref(a));//error

2 detach传实参的类型测试
当实参为普通对象时:

1)当形参为普通对象时:拷贝两次。
在这里插入图片描述
2)当形参为引用时:拷贝一次。
在这里插入图片描述
3)当形参为指针时:无拷贝,并且多次执行非法访问m_i,打印的值为未确定值,非常危险,禁用。
在这里插入图片描述

当实参为临时对象时:

1)当形参为普通对象时:拷贝两次。这里注意一下:它每次输出结果都是正确的,即10,但是因为线程打印次序有时很乱,导致1和0错开。但是你打断点查看每次都是10。
在这里插入图片描述

2)当形参为引用时:拷贝一次,并且如果你多次运行,发现它每次都是在主线程执行完毕就已经拷贝构造完成。这个方法也是最安全的传参方法。
在这里插入图片描述

3)当形参为指针时:无拷贝,并且禁用,多次运行会出现未知的值。
可以看到,没有值是因为主线程已经结束了,线程与屏幕脱离关系。所以就导致指针再访问就出现问题。
在这里插入图片描述

当实参为引用时:

1)当形参为普通对象时:拷贝一次。危险操作。
在这里插入图片描述

2)当形参为引用时:无拷贝。危险操作。
在这里插入图片描述
3)当形参为指针时:无拷贝。危险操作,万万不能使用。并且传参失败。

thread mytobj(MyPrint, std::ref(a));//error
thread mytobj(MyPrint, &std::ref(a));//error

3 给出代码,自己一步步的安装上面传参即可,不要偷懒

#include<iostream>
#include<thread>
#include<string>

using namespace std;

class A{
public:
	mutable int m_i;

public:
	//类型转换构造函数,可以把一个int转换成一个类A对象。
	A(int a) :m_i(a){
		cout << "A::A(int a)构造函数执行!" << this << "threadid:" << std::this_thread::get_id() << endl;
	}

	A(const A &a) :m_i(a.m_i){
		cout << "A::A(A &a)复制构造函数执行!" << this << "threadid:" << std::this_thread::get_id() << endl;
	}

	~A(){
		cout << "A::~A()析构函数执行!" << this << "threadid:" << std::this_thread::get_id() << endl;
	}

	void thread_work(int num){
		cout << "子线程thread——work执行!" << this << "threadid:" << std::this_thread::get_id() << endl;
	}
};

//形参a
void MyPrint(const A a) {
	cout << "I am A" << endl;

	//打印多行是方便测试指针在主线程结束在线程非法访问m_i
	//cout << "I am A" << endl;
	//cout << "I am A" << endl;
	//cout << "I am A" << endl;
	//cout << "I am A" << endl;
	cout << a->m_i << endl;
}


int main(){
	
	//实参为thread参数2
	A a(10);
	thread mytobj(MyPrint, a);
	mytobj.join();

	return 0;
}

4 终极总结上面join和detach如何传参
下面这四点上一篇文章也总结过了。

  • 1)int型的直接值传递。
  • 2)指针绝不使用。
  • 3)传递类对象时,形参为引用,实参为匿名对象。形参为引用是防止多次拷贝,实参为匿名对象是防止子线程拷贝之前主线程提前结束。
  • 4)使用join上面问题均不出现。
  • 5)了解各种传参时的拷贝次数,拷贝次数看上图。

学完本篇,你可以熟练掌握线程如何传参。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

03C++11多线程编程之测试join,detach传各种实参时形参的拷贝次数 的相关文章

随机推荐

  • MATLAB实现控制系统模型(传递函数)的建立与转化,传递函数模型与零极点增益模型的转化,连续系统与离散系统的转化,对比不同采样周期对系统性能的影响

    最近使用MATLAB做了很多控制工程方面的仿真 测试不同系统的响应和特性 不得不说使用MATLAB做控制仿真还是十分简洁方便的 尤其是其中的simulink模块可以提供更加直观的模型 方便分析与测试 今天就分享在matlab中构造传递函数模
  • 【微信小程序】微信支付接入全流程

    一 前置条件 接入支付首先得需要有企业资质 并开通企业对公户 注册微信支付并进行对公户打款认证 二 开始接入 1 下载微信支付的AP证书 2 服务端接入微信支付 2 1 引入相关maven配置
  • Java基础之集合

    Java基础 集合 1 Collection接口 Collection 是 List 和 Set 的父接口 常用方法如下 package com java day16 import java util ArrayList import ja
  • 简单实现继承一个抽象类的同时实现接口

    定义一个抽象类animal author ljf 定义一个抽象类animal 关键字abstract public abstract class Animal 将动物共有属性进行封装 名字 年龄 颜色 性别 说话 private Strin
  • np.dot(a, b)用法

    In short np dot a b 就是一个乘法函数 数和数相乘 若a和b都是数 np dot 1 2 2 一维数组的内积 np dot 1 2 3 4 5 6 1 2 3 4 5 6 1x4 2x5 3x6 32 矩阵的乘积 x np
  • Unity学习笔记——TextMeshPro使用详解

    https blog csdn net elineSea article details 88799896 TextMesh Pro是Unity默认文本组件的替代品 TextMesh Pro和默认组件一样拥有高性能 它使用了完全不同的Sig
  • 为什么大部分人认为测试用例不重要?如何正确编写软件测试用例?

    如何编写测试用例似乎不是开发的重要部分 但是为了让一个软件测试人员最好地完成他们的工如如何编写测试用例似乎不是开发的重要部分 但是为了让一个软件测试人员最好地完成他们的作 他们需要一套清晰的步骤和一个被测试的东西的清晰定义 编写优秀的测试用
  • 代码审查常见代码质量问题

    配套的Bug解释模式 为了有针对性的使用这个工具 减少bug的误报 提高使用效率 我们选择了10个左右的bug模式 下面就是对这10个模式的解释 这些bug可能会引起程序的性能或逻辑问题 需要说明的是 findbugs能检测的bug pat
  • 有哪些好用的设计图工具?

    设计图纸制作软件是高级学习数字设计的最佳选择 无论你是想通过设计图纸制作软件创建一个明亮的设计 还是与其他设计师分享和交流 本文将介绍十个易于使用的设计图纸制作软件 其中大多数是初学者和高级艺术家 具有完整的绘图 照片编辑和小图形设计项目功
  • jmeter 安装_JMeter安装教程

    一 安装JMeter之前我们需要下载Java的jdk Java软件开发工具包 这是因为JMeter软件是由Java代码100 开发的 Java代码要运行必须依托于JVM Java虚拟机 因此JMeter如果要运行也必须要在有JVM环境的系统
  • STM32学习记录 中断

    STM32 中断非常强大 每个外设都可以产生中断 中断类型有 系统异常 外部中断 NVIC 嵌套向量中断控制器 属于内核外设 管理着包括内核和片上所有外设的中断相关的功能 两个重要的库文件 core cm3 h和misc h 中断编程的顺序
  • C语言文件操作详解

    目录 前言 一 文本数据和二进制数据 文本数据 二进制数据 文本文件和二进制文件 二 文件的打开和关闭 文件指针 打开文件 小细节 关闭文件 举个例子 注意事项 三 文本文件的读写 向文件中写入数据 举个例子 运行效果 从文件中读取数据 举
  • 什么是黑盒测试,和白盒测试的区别有哪些?

    软件测试是软件工程中的一个非常重要的环节 是开发项目整体的一部分 是伴随软件工程的诞生而诞生的 但软件测试不是万能的 不可能发现全部缺陷 其中 黑盒测试和白盒测试是两种不同类型的软件测试策略 它们具有同样强大的功能 白盒测试和黑盒测试往往不
  • 浅谈Android版本更新

    关于本文DownloadManager版本更新的源码链接详见我的开源项目AppUpdate 前言 版本升级对于app来讲已经是非常常见的功能了 每次项目的版本迭代 新功能的开发都需要下载更新新版本 通过安装新版本来实现我们的迭代 当然除了这
  • 图解Redis中的9种数据结构

    如图所示 Redis中提供了9种不同的数据操作类型 他们分别代表了不同的数据存储结构 图2 17 数据类型 String类型 String类型是Redis用的较多的一个基本类型 也是最简单的一种类型 它和我们在Java中使用的字符类型什么太
  • Quartz学习总结之核心接口Scheduler、Job

    参考文章 https www cnblogs com mengrennwpu p 7141986 html 核心接口如下 接口 含义 Scheduler scheduler的主要API接口 Job 任务实现接口 期望调度器能够执行 JobD
  • c++ oop构造函数与拷贝控制

    class Quote public Quote int x x x 如果我们删除的是一个指向派生类对象的基类指针 则需要虚析构函数 virtual Quote default 动态绑定析构函数 int x virtual void sho
  • [YOLO专题-18]:YOLO V5 - ultralytics代码解析-总体架构

    作者主页 文火冰糖的硅基工坊 文火冰糖 王文兵 的博客 文火冰糖的硅基工坊 CSDN博客 本文网址 https blog csdn net HiWangWenBing article details 122356975 目录 第1章 YOL
  • 多线程进阶

    同步与互斥 什么是同步 有序性 完整性 原子性 什么是互斥 什么是临界区 可以限制线程并发访问共享资源 达到同步与互斥目的的程序片段 阻隔线程 排斥线程 同步代码块 格式示例 使用说明 同步方法 使用格式 使用解释 示例代码 释放同步监视器
  • 03C++11多线程编程之测试join,detach传各种实参时形参的拷贝次数

    03C 11多线程编程之测试join detach传各种实参时形参的拷贝次数 首先我们看下面的总结测试图 然后一步步的测试 1 这里我们先测试join传实参的类型 当实参为普通对象时 1 当形参为普通对象时 拷贝了两次 2 当形参为引用时