并发编程之——多线程基础

  1、一些概念多线程

  线程,顾名思义,就是一条流水线工做的过程(流水线的工做须要电源,电源就至关于cpu),而一条流水线必须属于一个车间,一个车间的工做过程是一个进程,车间负责把资源整合到一块儿,是一个资源单位,而一个车间内至少有一条流水线。ide

  多线程(即多个控制线程)的概念是,在一个进程中存在多个线程,多个线程共享该进程的地址空间,至关于一个车间内有多条流水线,都共用一个车间的资源。例如,北京地铁与上海地铁是不一样的进程,而北京地铁里的13号线是一个线程,北京地铁全部的线路共享北京地铁全部的资源,好比全部的乘客能够被全部线路拉。spa

  那么,为何要开线程呢?当咱们须要多个程序同时运行,可是还须要数据共享——开进程的话能保证第一点可是数据不能共享,因此要用同一个进程下的多个线程。线程

  因此说,进程只是用来把资源集中到一块儿(进程只是一个资源单位,或者说资源集合),而线程才是cpu上的执行单位。光开进程不能工做,须要进程里开线程才能正常工做,当一个进程开启时,对应的一个线程会随着同时开启个进程能够开启多个线程————一个进程内的多个线程是共享数据的开进程的开销远远比开进程的开销大,由于开进程得申请空间,开线程是基于开好的空间进行的3d

  2、开启线程的两种方式code

  2.1 利用threading模块下的Thread类:对象

# -*- coding: utf-8  -*-
# -*- Author: WangHW -*-
from threading import Thread
import time
import os

def work(name):
    print('%s is running...id:%s'%(name,os.getpid()))
    time.sleep(1)
    print('%s is done...'%os.getpid())


if __name__ == '__main__':
    w = Thread(target=work,args=('whw',))
    #开启线程开始start方法
    w.start()
    #主进程开启是默认开启了主线程,进程要想执行必需要有一个线程
    #如今有一个进程两个线程
    #执行角度看这是主线程,资源角度讲是主进程
    print('主线程~')
View Code

  2.2 利用类的继承blog

# -*- coding: utf-8  -*-
# -*- Author: WangHW -*-
from threading import Thread
import time
import os

class MYThread(Thread):
    def __init__(self,name):
        super().__init__()
        self.name = name

    def run(self):
        print('%s is running...id:%s' % (self.name,os.getpid()))
        time.sleep(1)
        print('%s is done...'% os.getpid())


if __name__ == '__main__':
    w = MYThread('whw')
    #start
    w.start()
    print('主线程')
View Code

  3、线程与进程的区别:继承

  3.1 首先,从开销的角度来说,开进程的开销要远远大于开线程的开销,由于开进程涉及到空间的建立,而开启线程仅仅是在既有的空间的基础上进行的;其次,同一个进程的各个线程之间是共享资源的,而不一样的进程之间的资源是不共享的。进程

  3.2 咱们如今验证一下进程与线程的资源共享问题:

  3.2.1 对于多线程来讲:,咱们全局定义的n=100,而通过子线程t1的处理,n的值无论是在主线程仍是子线程都变成了0:

# -*- coding: utf-8  -*-
# -*- Author: WangHW -*-

from threading import Thread
import time
import os

n = 100

#方法
def work(name):
    print('%s is running...id:%s'%(name,os.getpid()))
    global n
    n = 0
    time.sleep(2)
    print('%s is done...'%os.getpid())
    print('%s 内n的值为:%s'%(os.getpid(),n))


if __name__ == '__main__':
    t1 = Thread(target=work,args=('子线程1',))
    t1.start()
    t1.join()

    print(''.center(10,'*'))
    print('主的n:',n)

  线程程序的运行结果:

  3.2.2 对于多进程来讲,多个进程之间是不共享资源的:

# -*- coding: utf-8  -*-
# -*- Author: WangHW -*-

from multiprocessing import Process
import time
import os

n = 100

#方法
def work(name):
    print('%s is running...id:%s'%(name,os.getpid()))
    global n
    n = 0
    time.sleep(2)
    print('%s is done...'%os.getpid())
    print('%s 内n的值为:%s'%(os.getpid(),n))


if __name__ == '__main__':
    p1 = Process(target=work,args=('子进程1',))
    p1.start()
    p1.join()

    print(''.center(10,'*'))
    print('主的n:',n)

  运行结果以下:

  4、Thread对象的其余属性及方法:

  Thread对象支持下列需求的方法:

  4.1 找到当前线程的名字与id:

  找到当前线程的名字须要引入current_thread类,用到getName方法:

print(current_thread().getName())

  而找id还能够利用os模块小的getpid方法:

print(os.getpid())

  4.2 查看当前存活的线程的名字与数量(注意须要在threading模块导入相应的类):

# 查看当前存活的线程
print(active_count())

#查看当前存活的具体的线程
print(enumerate())

  4.3 查看线程是否存活:

#造线程对象的时候能够用name=写名字
t = Thread(target=work,name='whw1')
t.start()
#查看线程是否存活
print(t.is_alive())

  4.4 设置线程名字

#造线程对象的时候能够用name=写名字
t = Thread(target=work,name='whw1')
t.start()
#设置线程的名字
t.setName('儿子线程1')
#设置主线程的名字
current_thread().setName('主线程')

  4.5 固然,还有join方法,等子线程执行完毕再执行主线程

 #造线程对象的时候能够用name=写名字
t = Thread(target=work,name='whw1')
t.start()
#等子线程执行完再执行主线程
t.join()
#找到主线程的名字--默认MainThread
print(''.center(10,'*'),current_thread().getName())

  具体的完整代码以及执行效果以下:

# -*- coding: utf-8  -*-
# -*- Author: WangHW -*-

from threading import Thread,current_thread,active_count,enumerate
import os
import time

def work():
    #找到当前线程的名字与id
    print('%s is running...id:%s:'%(current_thread().getName(),os.getpid()))
    time.sleep(2)
    print('%s is done...'%current_thread().getName())


if __name__ == '__main__':
    #造线程对象的时候能够用name=写名字
    t = Thread(target=work,name='whw1')
    t.start()
    # 查看当前存活的线程
    print('当前存活线程个数:',active_count())
    #查看当前存活的具体的线程
    print('当前存活线程的具体信息:',enumerate())
    #查看线程是否存活
    print('子线程是否存活?',t.is_alive())
    #设置线程的名字
    t.setName('儿子线程1')

    #等子线程执行完再执行主线程
    t.join()

    # 查看子线程是否存活
    print('子线程是否存活?',t.is_alive())
    #查看当前存活的线程
    print('当前存活线程个数:',active_count())
    # 查看当前存活的线程
    print('当前存活线程的具体信息:',enumerate())
    #设置主线程的名字
    current_thread().setName('主线程')
    #找到主线程的名字--默认MainThread
    print(''.center(10,'*'),current_thread().getName())
Thread对象的方法

  执行效果:

相关文章
相关标签/搜索