title: How to make use of a multiprocessing manager within a class
body: <p>To start with, here is some code that works</p>
  <pre class="lang-py prettyprint-override"><code>from multiprocessing import Pool, Manager
  import random
  
  manager = Manager()
  dct = manager.dict()
  
  def do_thing(n):
      for i in range(10_000_000):
          i += 1
      dct[n] = random.randint(0, 9)
  
  with Pool(2) as pool:
      pool.map(do_thing, range(10))
  </code></pre>
  <p>Now if I try to make a class out of this:</p>
  <pre class="lang-py prettyprint-override"><code>from multiprocessing import Pool, Manager
  import random
  
  
  class SomeClass:
      def __init__(self):
          self.manager = Manager()
          self.dct = self.manager.dict()
  
      def __call__(self):
          with Pool(2) as pool:
              pool.map(self.do_thing, range(10))
  
      def do_thing(self, n):
          for i in range(10_000_000):
              i += 1
          self.dct[n] = random.randint(0, 9)
  
  
  if __name__ == '__main__':
      inst = SomeClass()
      inst()
  </code></pre>
  <p>I run into: <code>TypeError: Pickling an AuthenticationString object is disallowed for security reasons</code>. Now from <a href="https://stackoverflow.com/questions/29007619/python-typeerror-pickling-an-authenticationstring-object-is-disallowed-for-sec">here</a>, I get the hint that Python is trying to pickle the <code>Manager</code> which as I understand has its own dedicated process, and processes can't be pickled because they contain an <code>AuthenticationString</code>.</p>
  <p>I don't know enough about how forking works (I'm on Linux, so I understand this is the default method for starting new processes) to understand exactly why the <code>Manager</code> instance needs to be pickled.</p>
  <p><strong>So here are my questions:</strong></p>
  <ol>
  <li>Why is this happening?</li>
  <li>How can I use a <code>Manager</code> when doing multiprocessing within a class? PS: I want to be able to import SomeClass from this module.</li>
  <li>Is what I'm asking for unreasonable or unconventional?</li>
  </ol>
  <p>PS: I know I can do this exact snippet without the <code>Manager</code> by exploiting the fact that <code>pool.map</code> will return things in order, so something like this: <code>res = pool.map(self.do_thing, range(10))</code> then <code>dct = {k: v for k, v in zip(range(10), res)}</code>. But that's besides the point of the question.</p>