02-线程

目标

  • 能够理解主线程和子线程关系
  • 知道使用 threading.Thread 类能够创建线程对象
  • 知道 threading.Thread 的 target 参数能够指定线程执行的任务

1. 线程概念

线程,可简单理解为是程序执行的一条分支,也是程序执行流的最小单元。线程是被CPU独立调度和分派的基本单位,线程自己不拥有系统资源,只拥有一点儿在运行中必不可少的资源,但它可与同属一个进程的其它线程共享进程所拥有的全部资源。

image-20180907173129468

主线程:

当一个程序启动时,就有一个进程被操作系统(OS)创建,与此同时一个线程也立刻运行,该线程通常叫做程序的主线程,简而言之:程序启动就会创建一个主线程。

主线程的重要性有两方面: 1)是产生其他子线程的线程; 2)通常它必须最后完成执行比如执行各种关闭动作。

子线程

可以看做是程序执行的一条分支,当子线程启动后会和主线程一起同时执行

2. 单线程执行

import time


def saySorry():
    print("亲爱的,我错了,我能吃饭了吗?")
    time.sleep(1)


if __name__ == '__main__':

    for i in range(5):
        saySorry()

运行结果:

02-就业班-01-6

3. 使用threading模块 创建子线程

python的thread模块是比较底层的模块,python的threading模块是对thread做了一些包装的,可以更加方便的被使用

3.1 核心方法

  • threading.Thread(target=函数名) threading模块的Thread类 创建子线程对象
  • 线程对象.start() 启动子线程

3.2 代码实现

import time
import threading

def saySorry():
    print("亲爱的,我错了,我能吃饭了吗?")
    time.sleep(1)


if __name__ == '__main__':

    for i in range(5):
        # 创建子线程的的方法
        # 1、导入 threading 模块
        # 2、使用 threading.Tread() 方法,创建子线程对象
        # threading.Thread(target=函数名, args=(参数列表,元组))
        t1 = threading.Thread(target=saySorry)
        # 3、使用子线程对象调用start() 方法,可以开启子线程(子线程将同时执行)
        t1.start()

    print("我是主线程")

运行结果:

02-就业班-01-5

说明

  1. 可以明显看出使用了多线程并发的操作,花费时间要短很多
  2. 当调用start()时,才会真正的创建线程,并且开始执行
  3. 每个线程都有一个唯一标示符,来区分线程中的主次关系
  4. 主线程:mainThread,Main函数或者程序主入口,都可以称为主线程
  5. 子线程:Thread-x 使用 threading.Thread() 创建出来的都是子线程
  6. 线程数量:主线程数 + 子线程数

image-20180701090841816

4. 主线程会等待所有的子线程结束后才结束

#coding=utf-8
import threading
from time import sleep,ctime

def sing():
    for i in range(3):
        print("正在唱歌...%d"%i)
        sleep(1)

def dance():
    for i in range(3):
        print("正在跳舞...%d"%i)
        sleep(1)

if __name__ == '__main__':
    print('---开始---:%s'%ctime())

    t1 = threading.Thread(target=sing)
    t2 = threading.Thread(target=dance)

    t1.start()
    t2.start()

    #sleep(5) # 屏蔽此行代码,试试看,程序是否会立马结束?
    print('---结束---:%s'%ctime())

18