主线程与线程管理:理解CreateThread及线程关闭

需积分: 10 0 下载量 81 浏览量 更新于2024-07-14 收藏 883KB PPT 举报
"主线程的创建和管理以及预处理概念在IT行业中是至关重要的。线程是操作系统调度的基本单元,允许程序并发执行多个任务。预处理则是在编译过程中的一个阶段,处理源代码中的宏定义、条件编译指令等。在主线程中,我们通常进行程序的主要逻辑和管理工作,而通过创建线程可以实现特定任务的异步处理,例如在给定的描述中,创建了一个用于接收输入的线程。" 在Windows API中,`CreateThread()`函数用于创建一个新的线程。这个函数需要几个参数,包括线程属性、栈大小、线程入口点(即线程开始执行的函数,这里使用了`getInput`)、传递给线程函数的参数、创建标志以及返回的线程ID。`NULL`通常表示使用默认的线程属性,`0`表示默认的栈大小。`LPTHREAD_START_ROUTINE`是一个指向线程函数的指针类型,它接受`LPVOID`类型的参数,因为线程函数可能需要接收任何类型的数据,所以使用`LPVOID`作为通用参数。 `DWORD`是Windows API中定义的一种数据类型,它是一个32位无符号整数,用于表示各种计数值或状态。在创建线程时,`ThreadID`变量用来存储新创建线程的唯一标识符。 线程管理中,`HANDLE`类型的句柄是操作系统用来标识和操作对象(如线程、进程)的特殊标识。在创建线程后,我们需要保持对线程句柄的引用,直到不再需要它。一旦线程完成其工作,应该使用`CloseHandle()`函数关闭线程句柄,减少线程内核对象的引用计数。这是因为在线程结束时,如果不关闭句柄,它的引用计数不会减少到零,导致内核对象无法被及时释放,可能会占用不必要的系统资源。因此,良好的编程习惯是及时关闭不再使用的线程句柄。 预处理在编程中扮演着基础的角色。在C/C++语言中,预处理器(cpp)会在编译器实际编译源代码之前先处理源文件。它负责展开宏定义、包含头文件、处理条件编译指令等。预处理可以帮助程序员编写可复用且灵活的代码,例如通过宏定义来设置常量、简化复杂的表达式,或者通过条件编译来针对不同的平台或配置选择不同的代码路径。 总结来说,理解并熟练掌握线程管理和预处理是成为一名合格的IT专业人员的基础,它们是编写高效、可维护代码的关键元素。无论是创建和管理线程以提高程序的并发性,还是使用预处理来增强代码的灵活性和可移植性,都是软件开发中不可或缺的技能。
2023-06-12 上传

package step2; import java.util.concurrent.Callable; import java.util.concurrent.ExecutionException; import java.util.concurrent.FutureTask; // ---------------------Begin------------------------ //tips: 输出语句为:Thread.currentThread().getName()+"的call()方法在运行" //定义一个实现Callable接口的实现类,类名必须命名为MyThread_callable class MyThread_callable<T> implements Callable<T> { public T call() throws Exception { return (T) (Thread.currentThread().getName() + "的call()方法在运行"); }} // ---------------------End------------------------ public class CallableExample { public static void main(String[] args) throws InterruptedException, ExecutionException { // 创建Callable接口的实现类对象 MyThread_callable myThread3 = new MyThread_callable(); // 使用FutureTask封装Callable接口 FutureTask<Object> ft1 = new FutureTask<>(myThread3); // 使用Thread(Runnable target ,String name)构造方法创建线程对象 Thread thread1 = new Thread(ft1, "thread1"); // 创建并启动另一个线程thread2 FutureTask<Object> ft2 = new FutureTask<>(myThread3); Thread thread2 = new Thread(ft2, "thread2"); // ---------------------Begin------------------------ // 调用线程对象的start()方法启动线程 System.out.println(thread1.start()) ; System.out.println(thread2.start()) ; // 可以通过FutureTask对象的方法管理返回值 Object result1 = ft1.get(); Object result2 = ft2.get(); System.out.println(result1); System.out.println(result2); // ---------------------End------------------------ } }

2023-06-11 上传

#include<iostream> #include<Windows.h> #include <iomanip> #include <math.h> using namespace std; float x=0; DWORD WINAPI Thread1(LPVOID lpParameter); DWORD WINAPI Thread2(LPVOID lpParameter); void f1() { int i=10; while(i--) cout<<"i="<<i<<endl; } void f2() { int j=20; while(j--) cout<<"j="<<j<<endl; } int main() { cout<<"主线程已启动"<<endl; //f1(); //f2(); HANDLE hThread1=CreateThread(NULL,0,Thread1,NULL,0,NULL);//启动线程1 HANDLE hThread2=CreateThread(NULL,0,Thread2,NULL,0,NULL);//启动线程2 CloseHandle(hThread1);//关闭线程1 CloseHandle(hThread2);//关闭线程2 int i=25; while(i--) { cout<<"主线程运行中"<<endl; Sleep(100);//延时0.1s } //CloseHandle(hThread1);//关闭线程1 //CloseHandle(hThread2);//关闭线程2 system("pause");//暂停防止程序退出 return 0; } DWORD WINAPI Thread1(LPVOID lpParameter) { // cout<<"线程1已启动"<<endl; // //int i=5; // //while(i--) // //{ // //cout<<"线程1运行中"<<endl; //cout<<"i1="<<i<<endl; //Sleep(100);//延时0.1s // //} int i=0; while(i<101) { x=x+0.02; i++; Sleep(100);//延时0.1s } return 0; } DWORD WINAPI Thread2(LPVOID lpParameter) { // cout<<"线程2已启动"<<endl; // //int i=100; // //while(i--) // //{ // //cout<<"线程2运行中"<<endl; ////cout<<setw(i*10)<<"*"<<endl; //cout<<"i2="<<i<<endl; //Sleep(100);//延时0.1s // //} int i=0; while(x<=2.0) { //cout<<setw(30*sin(x))<<"*"<<endl; cout<<x<<endl; Sleep(100);//延时0.1s } return 0; }在所给线程代码的基础上,修改: (1)一个线程负责数的变化,从0变到4*3.14159,步长为0.02; (2)一个线程负责读取系统时间; (3)一个线程负责将数的正弦、余弦与正要值计算并显示,同时显示系统时间; (4)步长停顿100ms。 要求:用console程序。

2023-05-30 上传