c++如何在主线程退出后马上退出子线程_c++线程让主线程等待子线程退出在退出 - CSDN
精华内容
参与话题
  • 对于WINDOWS系统,主线程退出,其他未执行完毕的子线程也会退出,因为主线程退出调用exit(),相当于终止整个进程,其他线程自然而然会终止;...所以,我们应该在主线程退出之前等待其他子线程执行完毕...
    1. 对于WINDOWS系统,主线程退出,其他未执行完毕的子线程也会退出,因为主线程退出调用exit(),相当于终止整个进程,其他线程自然而然会终止;
    2. 对于linux系统,主线程退出,其他未执行完毕的子线程不会退出,会继续执行,但是这个进程会编程僵尸进程,通过ps -ef查看进程列表,如果有defunct字样的进程,就是僵尸进程。僵尸进程应该被避免。所以,我们应该在主线程退出之前等待其他子线程执行完毕,具体做法有:
      可以在主线程return之前调用phread_exit(),会使主线程退出,子线程继续执行,当所有线程执行完毕,进程才会退出。
    3. 为什么windows系统跟Linux系统有不一样的差别呢?
      据我分析,可能有的linux系统线程还是用进程实现的,而进程与进程是独立的,所以主线程的退出不影响其他线程,gdb调试时,如果看到LWP字样,它的意思是Light Weight Process,轻量级进程,就是线程,可见该线程是通过进程实现的。
      Linux内核2.4版本以前,线程的实现和管理方式是按照进程的方式来的。

      没有

       

    展开全文
  • 若只是主线程退出,仍要分两种情况分析:实际上主线程退出后子线程的状态依赖于它所在的进程,如果进程没有退出的话子线程依然正常运转。如果进程退出了,那么它所有的线程都会退出,所以子线程也就退出了。 查看...

    分清两个概念
    主线程和当前进程的关系:当前进程由主线程和若干个子线程组成。
    若当前进程退出后,子线程也会跟着一起退出;若只是主线程退出,仍要分两种情况分析:实际上主线程退出后子线程的状态依赖于它所在的进程,如果进程没有退出的话子线程依然正常运转。如果进程退出了,那么它所有的线程都会退出,所以子线程也就退出了。

    查看进程、线程方式

    进程:
    ps -elf | grep "对应的文本内容"
    ps aux    ——查看运行的进程
    
    线程:
    ps -T -p 进程号
    top -H  -p 进程号(sspid对应的为线程号)
    
    Linux下获取当前线程ID号函数:
    pthread_t pthread_self();
    

    1、若主进程、主线程和子线程都未挂时
    进程线程不退出
    进程线程不退出2
    2、若主进程退出,主线程和子线程未进行操作,则:
    主进程退出主进程退出2

    3、若主进程不退出,主线程退出(被杀死),子线程未操作,则

    主线程退出
    主线程退出2
    结论:
    子线程的清理只与当前进程是否被销毁有关,跟主线程销毁无关。

    展开全文
  • c++主线程子线程

    千次阅读 2020-01-29 10:15:02
    c++主线程和子线程 最近学习c++多线程,写一篇博客记录下自己的收获。 一.main()函数是主线程函数,main()函数中创建的线程属于子线程,那主线程和子线程的优先级谁更高呢? 可以看下另外一篇文档:link ...

    c++主线程和子线程

    最近在学习c++多线程,写一篇博客记录下自己的收获。
    一.main()函数是主线程函数,在main()函数中创建的线程属于子线程,那主线程和子线程的优先级谁更高呢?
    可以看下另外一篇文档:link
    在一个线程中开启另外一个新线程,则新开线程称为该线程的子线程,子线程初始优先级与父线程相同。不过主线程先启动占用了cpu资源,如果存在主线程和子线程争抢cpu执行权的话,看运气,谁抢到就让谁执行。
    其实设置了优先级,也无法保障线程的执行次序。只不过,优先级高的线程获取CPU资源的概率较大,优先级低的并非没机会执行。 线程的优先级用1-10之间的整数表示,数值越大优先级越高,默认的优先级为5。
    下面来看一段简单的代码:

    #include "stdafx.h"
    #include <iostream>
    #include "process.h"
    #include "windows.h"
    using namespace std;
    
    void ThreadFun1(void *){
    	cout << "这是子线程1" << endl;
    }
    void ThreadFun2(void *){
    	cout << "这是子线程2" << endl;
    }
    int main(){     	
    	_beginthread(ThreadFun1, 0, NULL); 
    	_beginthread(ThreadFun2, 0, NULL);    
    	cout << "end" << endl;
    	return 0;  
    }
    

    这里定义了两个线程函数,并在主线程main()中创建了两个子线程。于是,此进程中有三个子线程,任一时刻cpu只运行一个进程,当cpu轮换到此进程时,到此会执行三个线程中哪一个呢?
    多次运行结果如下:
    在这里插入图片描述
    可见,主线程总是能优先获得cpu的执行权,且主线程执行完成后,程序就退出了,子线程就再也没有执行的机会,即主线程结束,子线程也会被迫结束
    为了让主线程获得cpu的执行权之后,程序不退出,可以在主线程中加入一个死循环,代码如下:

    #include "stdafx.h"
    #include <iostream>
    #include "process.h"
    #include "windows.h"
    using namespace std;
    
    void ThreadFun1(void *){
    	cout << "这是子线程1" << endl;
    }
    void ThreadFun2(void *){
    	cout << "这是子线程2" << endl;
    }
    int main(){     	
    	_beginthread(ThreadFun1, 0, NULL); 
    	_beginthread(ThreadFun2, 0, NULL);  
    	cout << "end" << endl;
    	while(1){}
    	return 0;  
    }
    

    这样在第一回合的cpu争夺中,主线程获得执行权后程序也不会退出,在后续的cpu争夺回合中,子线程便有机会获得cpu的执行权。 程序的执行结果如下:
    在这里插入图片描述在这里插入图片描述
    第一次争夺中,主线程获得cpu执行权,然后执行循环,后续争夺中,某一回合子线程1或者2获得执行权(这里由于子线程内容较少,在一次时间片轮换中就把子线程执行完毕,即只要获得一次cpu执行权就可以执行完子线程),然后退出线程池,剩下的一个子线程和主线程继续争夺cpu的执行权,后面某一个回合中,剩下子线程也执行完毕,只剩下了主线程,便一直执行主线程中的循环。
    而且也可以看出,两个子线程的执行顺序不定,即哪个子线程能先获得cpu的执行权得看运气。

    二、如果想先执行子线程,然后执行主线程,应该采用什么方法?
    这里介绍一个Sleep()函数,Sleep()函数的解释可以看这篇博客:link
    大致内容如下:
    当调用Sleep函数的时候,比如Sleep(400);它告诉系统,此线程将放弃此次运行的时间片,比方说现在线程只执行了10ms,按“有关部门规定”它被唤醒一次是要执行20ms的。这时它就说,这次机会我放弃,后面的10ms不要了。下次轮上我再叫我。 这样,系统便会将其终止,然后再一次进行调度选择。如果它运气很好,又被选中了,系统则会查看这个线程是否处于sleep标志中。如果发现他还需要继续睡眠,则重新进行调度选择,直到选择一个有权执行的线程为止。 如果很不幸,400ms到了,但是系统很忙,调度算法在很长一段时间也没有选择到这个线程,那这么线程就很继续休眠。于是说,这个Sleep(400);将导致这个线程会休眠大于等于400MS的时间。

    关于这个函数更具权威的解释(抄书):
    1、调用Sleep,可使线程自愿放弃它剩余的时间片。
    2、系统将在大约的指定秒数内使线程不可高度。不错,如果告诉系统,想睡眠100MS,那么可以睡大约这么长的时间,但也也可能睡眠数秒或数分钟。记住,WINDOWS不是个实时操作系统。虽然线程可能在规定的时间被唤醒,但是它能否做到,取决于系统中还有什么操作正在进行。
    3、可以调用Sleep(INFINITE),告诉系统永远不要调用这个线程。但最好不要这样,让线程退出就行了。反正你都不再需要它。或者调用Sleep(0);告诉系统线程将放弃剩于的时间片,并使系统调度另一个线程。但是,系统可以对刚刚调用Sleep的线程重新调度。如果不存在多个拥有相同优先级的可调度线程。就会出现这种情况。

    加入Sleep()函数后的代码如下:

    #include "stdafx.h"
    #include <iostream>
    #include "process.h"
    #include "windows.h"
    using namespace std;
    
    void ThreadFun1(void *){
    	while (1) {
    		cout << "这是子线程1" << endl;
    		Sleep(30);
    	}
    }
    int main(){     	
    	_beginthread(ThreadFun1, 0, NULL); 
    	Sleep(300);
    	cout << "end" << endl;
    }
    

    在这里插入图片描述
    可以这么理解:主线程Sleep 300毫秒,在这300毫秒内,程序只能执行子线程,然而子线程执行完打印后,也进入Sleep(30),可以认为时是每30毫秒执行一次子线程。
    如果把Sleep(30)放在cout之前;子线程执行9次,这个细微的差别请读者自行理解 。
    最后可以让三个线程依次执行:

    #include "stdafx.h"
    #include <iostream>
    #include "process.h"
    #include "windows.h"
    using namespace std;
    
    void ThreadFun1(void *){
    	cout << "这是子线程1" << endl;
    }
    void ThreadFun2(void *) {
    	Sleep(30);
    	cout << "这是子线程2" << endl;
    }
    
    int main(){     	
    	_beginthread(ThreadFun1, 0, NULL); 
    	_beginthread(ThreadFun2, 0, NULL);
    	Sleep(300);
    	cout << "end" << endl;
    }
    

    运行结果如下:
    在这里插入图片描述
    写在最后:
    Sleep()函数并不能严格保证线程按顺序执行,如上面的程序,如果子线程1内容很多,代码无法在30毫秒内完成,因此当子线程2休眠完毕后,两个子线程依然会继续争夺cpu。故无法保证线程能按顺序执行。

    展开全文
  • 进程与主线程: 首先得明确一点,我理解的进程是一个exe文件运行之后的独立...答案:主线程退出可能会间接导致子线程退出!但不会直接导致子线程退出! 因为主线程退出分两种情况: (1) 不对主线程做任务特殊处理,当其..

    1.进程与主线程:
    首先得明确一点,我理解的进程是一个exe文件运行之后的独立资源,每个进程有且仅有一个主线程,进程是负责分配资源的,线程是负责执行资源的(一般可以认为线程的执行时间就是线程调度函数的运行时间),相当于进程是包工头,线程是干活的工人,在后文里,不做特殊说明,子线程统一都是由主线程直接或间接创建的。

    2.主线程结束后,其它子线程是立刻退出还是继续执行?
    答案:主线程退出可能会间接导致子线程退出!但不会直接导致子线程退出!
    因为主线程退出分两种情况:
    (1) 不对主线程做任何特殊处理,当其正常结束后,主进程也会结束,从而间接导致其它子线程的执行资源被回收,子线程也全部结束运行。

    我自己做了一个测试来验证这个结果,创建线程的属性也基本是项目里常用的,代码如下,主函数就是主线程的执行资源,地球人都知道,就不啰嗦了:
    在这里插入图片描述

    对于这个代码,主线程肯定是比子线程先退出的,它执行10秒,其它的子线程执行40秒,配合任务管理器来观察,如果”主线程”文字打印完之后,控制台直接关闭而不是继续等待,并且任务管理器里的进程也结束了,那就说明之前的推论是正确的,下面是运行之后的情况;

    程序刚运行时,控制台和任务管理器如下:
    在这里插入图片描述

    10秒过后,控制台消失,任务管理器里也没有”ClassTest”进程了:
    在这里插入图片描述
    这种情况下,主线程正常退出后,其它子线程也不能执行了!

    (2) 调用API去关闭主线程时,主进程不会退出,其它子线程会正常执行。
    在这里插入图片描述
    对于上面的代码,运行时的截图跟之前一样,但是主线程是被API结束的,不是正常退出,10秒过后,控制台没有退出,任务管理器里”ClassTest”进程还在,线程数量减少,说明三个子线程还在:
    在这里插入图片描述
    3. 子线程退出是否会互相影响?
    答案是不会,有一点得明确,假如线程A创建了线程B,它俩就是单独的两个线程了,A的退出不会影响B,B的退出也不会影响A。可以理解为工地的工人工作量太大,他可以另外拉一个工人(线程)来帮自己干活,工资还是由包工头(主进程)来负责;就像我们组老大(子线程A)只负责拉我(子线程B)来干活,但是工资是老板 (主进程)来发。

    综上所述:
    (1) 主线程的退出对其它线程并没有直接影响;主线程被提前强制结束时,不会导致进程退出,其他子线程会正常执行;主线程正常结束时,会导致进程退出,从而回收进程资源,其他子线程也都退出(这种现象看起来像是主线程直接导致子线程结束,不能弄混了)。
    (2) 子线程退出不会对别的线程直接造成影响,因为主进程还在,只不过可能因为数据共享等问题给别的线程造成一些麻烦。

    By the way:
    很多人用VS测试的时候,会在主函数末尾加上system(“pause”)或getchar()不让控制台结束,我想了想,做这个测试的时候不能用这两个方法,因为它们会导致主线程阻塞,那这样一来主线程不退出,这个测试就没法做了……我刚开始就是犯了这个错误….

    展开全文
  • 1 #include <windows.h> 2 #include <process.h> /* _beginthread, _endthread */ 3 #include <iostream> 4 5 using namespace std; 6 7 void show(void *ptr);... 9 int ma...
  • 主线程退出之前会发出通知,其余还运行的线程接到通知会自行退出。现在,主线程需等待其余线程安全退出,怎么办? . 最容易想到的办法是,主线程CreateThread,将返回的句柄加入一个列表。主线程终止之前,...
  • 主线程退出后,子线程会不会退出

    万次阅读 2016-05-26 17:34:43
    额,好吧,这是个标题党,其实所有的线程都是平级的,根本不存在主线程子线程。下文所述为了方便,将main函数中的线程看做主线程,其它线程看成子线程,特此说明。先考虑以下代码:   #include #include #...
  • C++ thread退出线程 多线程 子线程控制退出主线程 window VS2017 Debug Error! Abort() has been called. C++ thread退出线程 多线程 子线程控制退出主线程 window VS2017 Debug Error! Abort() has been called.
  • 目录 主线程退出 主线程随进程一起退出 ...对于程序来说,如果主进程在子进程还未结束时就已经退出,那么Linux内核会将子进程的父进程ID改为1(也就是init进程),当子进程结束会由init进程来回收该...
  • Linux中主线程子线程的终止次序

    千次阅读 2018-11-29 15:47:52
    Linux中pthread是我们进行多线程并发时经常使用的...主线程退出,子线程可以继续执行;子线程退出,主线程也可以继续执行。  (2)程序加载到内存中执行的时候,进程就会生成一个主线程。虽然主线程和子线程之间没...
  • 我所知道的不让主线程退出的方法有: 一,死循环:while(1);/ for(;;); 二,pause(); 让主线程暂停等待信号使其退出 三,另一种死循环while(1)sleep(100) 四,通过信号量,使其通过等待一个不可能的发生的信号来...
  • 主线程等待子线程执行完再结束

    千次阅读 2018-09-04 16:28:00
    主线程子线程1–子线程1的子线程1 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; | &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; |-子线程1的子线程2 &nbsp; ...
  • 这个根据具体情况二定: 1、父线程主线程,则父线程退出后, 子线程一定会退出。 2、父线程不是主线程,则父线程退出后, 子线程不会退出
  • 我所知道的不让主线程退出的方法有: 一,死循环:while(1);/ for(;;); 二,pause(); 让主线程暂停等待信号使其退出 三,另一种死循环while(1)sleep(100) 四,通过信号量,使其通过等待一个不可能的发生的信号来阻塞...
  • 今天做实验的时候需要用到多线程,于是去搜了一些过于C++线程编程的知识。 了解到,在C++11中,添加了新库来支持多线程: #include <thread> 创建新线程的方法如下: std::thread t(function) 其中 ...
  • 但是当应用程序退出时,总归还是要关闭所有的子线程,所以还是要面临如何解决从子线外部关闭子线程的问题。 因为之前只接触过Linux的系统编程和网络编程,纯C语言的编程,很直接的去用pthread_cancel函数,搭配...
  • pthread 主线程子线程退出关系

    千次阅读 2017-09-14 14:31:15
    我们一个线程中经常会创建另外的新线程,如果主线程退出,会不会影响它所创建的新线程呢?下面就来讨论一下。1、 主线程等待新线程先结束退出,主线程退出。正常执行。 实例代码:#include "apue.h" #include ...
  • 面试题:如何优雅的在主线程中结束一个从线程?: 假如现在一个线程阻塞了,主线程要结束点从线程,怎么办? —回答:调用pthread_cancel()终止它 线程退出方式: 1. 从线程函数中return(不适合主线程); ...
  • 原文地址已经找不到了 ...但是所谓的"主线程"main,其入口代码是类似这样的方式调用main的:exit(main(...))。 main执行完之后, 会调用exit()。 exit() 会让整个进程over终止,那所有线程自然都会退出
1 2 3 4 5 ... 20
收藏数 15,832
精华内容 6,332
关键字:

c++如何在主线程退出后马上退出子线程