2013-05-21 2 views
0

Я пытаюсь синхронизировать несколько процессов с помощью семафоров. Я думал, что вместо того, чтобы создать функцию для каждого процесса, можно было бы в более общем виде, с одной функцией и некоторыми аргументами для зависимостей:Синхронизация процесса в Python

import multiprocessing 
from multiprocessing import * 

class Worker: 
    def __init__(self, size): 
     self._semaphores = [Semaphore(0)]*(size + 1) 

    def run(self, name, acquire, release): 
     for i in acquire: 
      self._semaphores[i].acquire() 

      print('Running', name) 

     for i in release: 
      self._semaphores[i].release() 

В этом случае я получил пять процессов. Первый начинается первым, вторым и третьим после первого, четвертым после второго и третьего, а пятым после четвертого.

if __name__ == '__main__': 
    worker = Worker(5) 
    Process(target=worker.run, args=('5', [5], [])).start() 
    Process(target=worker.run, args=('4', [4,4], [5])).start() 
    Process(target=worker.run, args=('3', [3], [4])).start() 
    Process(target=worker.run, args=('2', [2], [4])).start() 
    Process(target=worker.run, args=('1', [], [2,3])).start() 

Ожидаемый результат будет:

Running 1 
Running 2 
Running 3 
Running 4 
Running 5 

Но синхронизация не работает, как ожидалось. Выполнение является случайным, включая взаимоблокировки. Почему это?

ответ

1

[Semaphore(0)]*(size + 1) создает список с size + 1 ссылками на одногоSemaphore объекта. Вы должны сделать различные экземпляры этого класса:

self._semaphores = [Semaphore(0) for _ in range(size + 1)] 
+0

Большое спасибо, это абсолютно правильно! Но есть одна мелочь, которую я не понимаю. Фиксированная версия не форсирует ожидаемый порядок. Таким образом, выход по-прежнему является случайным, но без взаимоблокировок в системе Windows. Есть идеи? – witrin

+0

@witrin: Я не совсем уверен, почему вам нужны семафоры. Почему бы вам не создать пул процессов и использовать 'pool.map_sync', чтобы вернуть результаты по порядку? – Blender

+0

Потому что это часть упражнения, которое требует использования семафоров. – witrin

0

Отступ отпечатке неверен, который предотвращает («Бег», «1»). После этого фиксируется 1 печать, за которой следуют 2 и 3, а затем 4, затем 5. 2 и 3 смешиваются, потому что они начинаются вместе, поэтому работа выполняется так, как ожидалось.