Python中基本同步原语的使用

Python中的同步原语--锁

from atexit import register
from random import randrange
from threading import Thread, Lock, current_thread
from time import ctime, sleep


class CleanOutputSet(set):
    def __str__(self):
        return ', '.join(x for x in self)


lock = Lock()
loops = (randrange(2, 5) for x in range(randrange(3, 7)))
remaining = CleanOutputSet()


def loop(nsec):
    myname = current_thread().name

    lock.acquire()
    remaining.add(myname)
    print('{} started {}'.format(ctime(), myname))
    lock.release()

    sleep(nsec)

    lock.acquire()
    remaining.remove(myname)
    print('{} Completed {} ({} secs)'.format(ctime(), myname, nsec))
    print('    (remaining: {})'.format(remaining or None))
    lock.release()


def main():
    print('starting at:', ctime())
    for pause in loops:
        Thread(target=loop, args=(pause,)).start()


@register
def _atexit():
    print('all done at:', ctime())


if __name__ == '__main__':
    main()

优化版使用上下文管理器:

...

def loop(nsec):
    myname = current_thread().name

    with lock:
        remaining.add(myname)
        print('{} started {}'.format(ctime(), myname))

    sleep(nsec)

    with lock:
        remaining.remove(myname)
        print('{} Completed {} ({} secs)'.format(ctime(), myname, nsec))
        print('    (remaining: {})'.format(remaining or None))

...

Python中的同步原语--信号量

from atexit import register
from random import randrange
from threading import BoundedSemaphore, Lock, Thread
from time import ctime, sleep


lock = Lock()
MAX = 5
candytray = BoundedSemaphore(MAX)


def refill():
    with lock:
        print('Refilling candy...')
        try:
            candytray.release()
        except ValueError:
            print('full, skipping')
        else:
            print('ok')


def buy():
    with lock:
        print('Buying candy...')
        if candytray.acquire(False):
            print('OK')
        else:
            print('empty, skipping')


def producer(loops):
    for x in range(loops):
        refill()
        sleep(randrange(3))


def consumer(loops):
    for x in range(loops):
        buy()
        sleep(randrange(3))


def _main():
    print('starting at:{}'.format(ctime()))
    nloops = randrange(2, 6)
    print('THE CANDY MACHINE (full with {} bars)!'.format(MAX))
    Thread(target=consumer, args=(randrange(nloops, nloops+MAX+2),)).start()
    Thread(target=producer, args=(randrange(nloops, nloops+MAX+2),)).start()


@register
def _atexit():
    print('all DONE at:', ctime())


if __name__ == '__main__':
    _main()
原文地址:https://www.cnblogs.com/BxScope/p/11000570.html