线程

补充知识点:

守护进程的例子

from multiprocessing import Process
import time,random


def runing():
    print('123')
    time.sleep(random.randint(1,3))
    print('end 123')

def runing1():
    print('456')
    time.sleep(random.randint(1,2))
    print('end 456')

if __name__ == '__main__':
    p1=Process(target=runing)
    p2=Process(target=runing1)

    p1.daemon=True
    p1.start()
    p2.start()

    print('主进程==》')

先说明一点,守护进程一定要在,strat之前加 不然会报错的,上面的例子 写了两个子进程,一个是守护进程,一个是普通的子进程,

我们都知道主进程 要等子进程,结束后,替儿子收尸,而守护进程要伴随主进程一生,(一生指的是主进程的执行期间)那上面的例子,运行的顺序

就是在主进程执行结束后,守护进程 就完成了自己的任务 死掉了,然后主进程一直等子进程死掉了,最后自己死掉了

线程:

1、什么是线程
    线程指的是一条流水线的工作过程

    进程根本就不是一个执行单位,进程其实是一个资源单位
    一个进程内自带一个线程,线程才是执行单位

2、进程VS线程
    1、同一进程内的线程们共享该进程内资源,不同进程内的线程资源肯定是隔离的
    2、创建线程的开销比创建进程要小的多

创建线程的两种方式

from threading import Thread
import time,random

def lack(name):
    print('%s is runing'%name)
    time.sleep(random.randint(1,3))
    print('%s end'%name)

if __name__ == '__main__':
    t=Thread(target=lack,args=('egon',))
    t.start()
    print('主线程--->')



class Mythread(Thread):
    def run(self):
        print('%s is runing' % self.name)
        time.sleep(random.randint(1, 3))
        print('%s end' % self.name)

if __name__ == '__main__':
    t=Mythread()
    t.start()
    print('主线程--->')

线程没有主次之分,称为主线程 是为了更好的区分

比较进程与线程的开销:

from threading import Thread
import time,os

def task():
    print('%s is running' %os.getpid())
    time.sleep(3)

if __name__ == '__main__':
    t=Thread(target=task,)
    t.start()
    print('主线程',os.getpid())
    #结果
    #10632 is running
    #主线程 10632
from multiprocessing import  Process

def task1():
    print('%s is running' % os.getpid())
    time.sleep(3)


if __name__ == '__main__':
    p=Process(target=task1)
    p.start()
    print('主进程', os.getpid())
    #结果
    #主进程 18036
    #16560 is running
#线程创建开销小

因为创建子进程,需要向操作系统发送请求,在等操作系统,去创建内存空间,在拷贝一份主进程的所有数据 没有线程在同一进程内,直接建一条

流水线来的快捷,所以创建进程比创建线程开销要大的多的多

比较进程与线程的隔离性:每个进程在内存空间都是有一块独立的内存空间的,互相隔离,数据不能共享的,但是线程的数据是可以共享的,通过下面的例子我们来证明一下:

#同一进程内的多个线程共享该进程内的资源

from threading import Thread
import time,os

x=1000
def task():
    global x
    x=0

if __name__ == '__main__':
    t=Thread(target=task,)
    t.start()
    t.join()
    print('主线程',x)#主线程 0

线程对象的其他方法

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

def task():
    print('%s is running' %current_thread().name)
    time.sleep(3)

if __name__ == '__main__':
    t1=Thread(target=task,name='第一个线程')
    t2=Thread(target=task,)
    t3=Thread(target=task,)
    t1.start()
    t2.start()
    t3.start()

    # print(t1.is_alive())
    print(active_count())#活跃的线程个数
    print(enumerate())#以列表的形式 打印出活跃的线程
    print('主线程',current_thread().name)#相当于实例化一个对象,取到它的名字

守护线程:

from threading import Thread
import time,random

def lack(name):
    print('%s is runing'%name)
    time.sleep(random.randint(1,3))
    print('%s end'%name)

if __name__ == '__main__':
    t=Thread(target=lack,args=('lxx',))
    t.daemon=True
    t.start()
    print('主线程--》')


def runing():
    print('123')
    time.sleep(3)
    print('end 123')

def runing1():
    print('456')
    time.sleep(1)
    print('end 456')

if __name__ == '__main__':
    t1=Thread(target=runing)
    t2=Thread(target=runing1)

    t1.daemon=True
    t1.start()
    t2.start()

    print('主线程==》')

守护进程和守护线程都是守护主的执行,但不一样的是主进程,print()执行就已经结束了,而主线程是除了守护线程以外的所有线程都执行完毕包括自己,才算执行完毕

线程斥互锁

from threading import Thread,Lock
import time

mutex=Lock()
x=100

def task():
    global x
    mutex.acquire()
    temp=x
    time.sleep(0.1)
    x=temp-1
    mutex.release()


if __name__ == '__main__':
    start=time.time()
    t_l=[]
    for i in range(100):
        t=Thread(target=task)
        t_l.append(t)
        t.start()
    for t in t_l:
        t.join()

    print('',x)
    print(time.time()-start)

死锁现象与递归锁

from threading import Thread,Lock,RLock
import time

# mutexA=Lock()
# mutexB=Lock()

mutexA=mutexB=RLock()

class MyThread(Thread):
    def run(self):
        self.f1()
        self.f2()

    def f1(self):
        mutexA.acquire()
        print('%s 拿到了A锁' %self.name)

        mutexB.acquire()
        print('%s 拿到了B锁' %self.name)
        mutexB.release()

        mutexA.release()

    def f2(self):
        mutexB.acquire()
        print('%s 拿到了B锁' %self.name)
        time.sleep(0.1)

        mutexA.acquire()
        print('%s 拿到了A锁' %self.name)
        mutexA.release()

        mutexB.release()


if __name__ == '__main__':
    for i in range(10):
        t=MyThread()
        t.start()

    # t1=MyThread()
    # t1.start()
    #
    # t2=MyThread()
    # t2.start()
    #
    # t3=MyThread()
    # t3.start()
    print('')

信号量

# from multiprocessing import Semaphore

from threading import Thread,Semaphore,current_thread
import time,random

sm=Semaphore(5)

def go_wc():
    sm.acquire()
    print('%s 上厕所ing' %current_thread().getName())
    time.sleep(random.randint(1,3))
    sm.release()

if __name__ == '__main__':
    for i in range(23):
        t=Thread(target=go_wc)
        t.start()

互斥锁和递归锁,每次都只能一个人来抢,而且 信号量,可以自己设置几个人同时来抢 

原文地址:https://www.cnblogs.com/yftzw/p/8954388.html