Python 多线程实现黑白棋子(python多线程解释)

本文通过黑白棋子游戏介绍Python多线程的两种情况,并探讨Python中的全局解释器锁(GIL)。GIL使得在Python中,即使在多核CPU上,多线程也无法实现真正的并行执行,只能交替运行。文章解释了GIL的工作原理以及其对I/O密集型和计算密集型程序的影响。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

◆问题描述

两个人下棋,一方执黑棋,一方执白棋。要求双方轮流下子。给出两种情况的解决办法:

1)执黑子一方先下
2)双方都可以先下,谁先抢到棋盘谁先下。然后开始轮流下子。

第一种情况

1)

贴代码:

import threading

import time

import random

b=threading.Semaphore(1)

w=threading.Semaphore(0)

def black():

    global b,w

    i=0

    while(i<5):

        b.acquire()

        i+=1

        print("black! ")

        print(i)

        w.release()

        time.sleep(random.random())


def white():

    global b,w

    j=0

    while(j<5):

        w.acquire()

        j+=1

        print("white! ")

        print(j)

        b.release()

        time.sleep(random.random())


if __name__=='__main__':

    black=threading.Thread(name='Black',target=black)

    white=threading.Thread(name='White',target=white)

    black.start();

    white.start();

运行结果:

第二种情况

2)

贴代码

import  threading

import random

import time


s=threading.Semaphore(1)

lock=threading.Lock()

def black():
    global bfg,wfg
    i=0
    fg=False
    s.acquire()
    if fg is not True:
        bfg = threading.Semaphore(1)
        wfg = threading.Semaphore(0)
        fg=True
    s.release()
    while(i<5):
        bfg.acquire()
        if lock.acquire():
            i+=1
            print("black!")
            wfg.release()
            lock.release()
        else:
            wfg.release()
            break
        time.sleep(random.random())


def white():
    
    global bfg, wfg
    
    j = 0
    
    fg = False
    
    s.acquire()
    
    if fg is not True:
        
        bfg = threading.Semaphore(0)
        
        wfg = threading.Semaphore(1)
        
        fg = True
        
    s.release()
    
    while (j < 5):
        
        wfg.acquire()
        
        if lock.acquire():
            
            j += 1
            
            print("white!")
            
            bfg.release()
            
            lock.release()
            
        else:
            
            bfg.release()
            
            break
            
        time.sleep(random.random())

if __name__ =='__main__':

    black = threading.Thread(name='Black', target=black)

    white = threading.Thread(name='White', target=white)

    a=random.randint(0,9)
    print(a)

    if(a<=4):

        black.start()

        white.start()

    else:

        white.start()

        black.start()





运行结果:

 

 

 

PS:

引用-->对于Python的解释:

作者:DarrenChan陈驰
链接:https://www.zhihu.com/question/23474039/answer/269526476
来源:知乎
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
 

Python中的多线程是假的多线程! 为什么这么说,我们先明确一个概念,全局解释器锁(GIL)。

Python代码的执行由Python虚拟机(解释器)来控制。Python在设计之初就考虑要在主循环中,同时只有一个线程在执行,就像单CPU的系统中运行多个进程那样,内存中可以存放多个程序,但任意时刻,只有一个程序在CPU中运行。同样地,虽然Python解释器可以运行多个线程,只有一个线程在解释器中运行。

对Python虚拟机的访问由全局解释器锁(GIL)来控制,正是这个锁能保证同时只有一个线程在运行。在多线程环境中,Python虚拟机按照以下方式执行。

1.设置GIL。

2.切换到一个线程去执行。

3.运行。

4.把线程设置为睡眠状态。

5.解锁GIL。

6.再次重复以上步骤。

对所有面向I/O的(会调用内建的操作系统C代码的)程序来说,GIL会在这个I/O调用之前被释放,以允许其他线程在这个线程等待I/O的时候运行。如果某线程并未使用很多I/O操作,它会在自己的时间片内一直占用处理器和GIL。也就是说,I/O密集型的Python程序比计算密集型的Python程序更能充分利用多线程的好处。

我们都知道,比方我有一个4核的CPU,那么这样一来,在单位时间内每个核只能跑一个线程,然后时间片轮转切换。但是Python不一样,它不管你有几个核,单位时间多个核只能跑一个线程,然后时间片轮转。看起来很不可思议?但是这就是GIL搞的鬼。任何Python线程执行前,必须先获得GIL锁,然后,每执行100条字节码,解释器就自动释放GIL锁,让别的线程有机会执行。这个GIL全局锁实际上把所有线程的执行代码都给上了锁,所以,多线程在Python中只能交替执行,即使100个线程跑在100核CPU上,也只能用到1个核。通常我们用的解释器是官方实现的CPython,要真正利用多核,除非重写一个不带GIL的解释器。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值