Python: Why do different threads get their own series of values ​​from a single generator?

I am learning multithreading in Python. I want to know how to provide data for multiple threads using generators. Here is what I wrote:

  import threading

  data = [i for i in xrange(100)]

  def generator():
      for i in data:
          yield i

  class CountThread(threading.Thread):
      def __init__(self, name):
          threading.Thread.__init__(self)
          self.name = name

      def run(self):
          for i in generator():
              print '{0} {1}'.format(self.name, i)

  a = CountThread('a')
  b = CountThread('b')
  a.start()
  b.start()

I thought the list would only be repeated once. But it seems that each thread interacts through the list independently.

exit:

a 0
a 1
a 2
b 0
a 3
a 4
b 1
b 2
a 5
a 6
a 7
a 8
a 9
b 3
b 4
b 5
b 6
b 7
b 8
...
(200 lines)

What is the reason for this? How can I rewrite a program so that the values ​​in the list are printed only once.

+3
source share
2 answers

You create a new generator in each thread in runusing this:

for i in generator():

each call generatorreturns a new instance of the generator:

>>> data = [i for i in xrange(10)]
>>> a, b = generator(), generator()
>>> id(a), id(b)
(37528032, 37527952)

a b :

>>> list(a), list(b)
([0, 1, 2, 3, 4, 5, 6, 7, 8, 9], [0, 1, 2, 3, 4, 5, 6, 7, 8, 9])

, , . , . , ValueError: generator already executing . Queue.Queue .

+9

Python. , . , , .

#!/usr/bin/python

import Queue
import threading

queueOfNumbers = Queue.Queue()

data = [i for i in xrange(100)]

def generator():
    for i in data:
        yield i

class CountThread(threading.Thread):
    def __init__(self, name, queue):
        threading.Thread.__init__(self)
        self.name = name
        self.queue = queue

    def run(self):
        i = self.queue.get()
        print '%s %s' % (self.name, i)


a = CountThread('a', queueOfNumbers)
b = CountThread('b', queueOfNumbers)
a.start()
b.start()

for num in generator():
    queueOfNumbers.put(num)

queueOfNumbers.join()

http://www.ibm.com/developerworks/aix/library/au-threadingpython/

0

All Articles