【问题标题】:Send method to subprocess发送方法到子进程
【发布时间】:2014-09-22 07:40:21
【问题描述】:

我正在使用 Twisted 实现一个进程池。最终目标是一个简单的 deferToProcess 函数,很像 deferToThread。我知道安瓿模块,但我避免使用它,因为它显然没有得到很好的维护,因为它需要 amp 子类,而且我有兴趣写这个。

我希望能够从 deferToProcess 调用当前项目中的任意静态函数。 Twisted 创建任意进程,所以我让它调用当前的 Python 解释器,并使用重复的导入路径。要查找模块级函数,您可以简单地确定该函数所在的模块,然后导入该模块并调用该函数。在我看来,将函数引用传递给静态类方法或 lambda 可能会很棘手。

为了弄清楚我的选择是什么,我查看了 Python 的多处理模块。我尝试过的一切都完美无缺,甚至是对父进程中全局对象的引用。

>>> class Test(object):
...     @staticmethod
...     def test():
...             print 'Found it!'
...
>>> p = multiprocessing.Process(target=Test.test, args=())
>>> p.start()
Found it!
>>> import sys
>>> p = multiprocessing.Process(target=lambda: sys.stdout.write('hello\r\n'), args=())
>>> p.start()
hello
>>> hm='Testing'
>>> p = multiprocessing.Process(target=lambda: sys.stdout.write(hm), args=())
>>> p.start()
Testing

很明显,Python 必须在所有数据完好无损的情况下分叉子进程。由于 Twisted 实际上产生了新的进程,是否有一种合理的方法来尝试恢复调用方法的完整路径,假设存在一个方法(例如方法不是动态的)?这包括静态模块级函数、分配给模块级变量的 lambda 函数和类的静态方法。我没有办法做到这一点

例如,运行假设函数

findCallPath(Test.test)

可能会回来

module.module.module.Test.test

提前致谢。

【问题讨论】:

  • 看来我可以用 Dill (pypi.python.org/pypi/dill) 序列化函数,但我仍然对我最初的问题感到好奇。
  • 请不要使用您的问题的标题来“标记”它。我已经编辑了标题。标记系统是确保对您的主题感兴趣的人看到您的问题的最佳方式。
  • “我知道安瓿模块,但我避免使用它,因为它显然没有得到很好的维护”——这不是不维护某些东西的好理由。这就是开源的工作方式——项目的所有权经常易手。
  • 我的意思是(根据谷歌的说法)安瓿模块存在一些问题,这些问题没有得到修复,并且在不久的将来不太可能修复,因为该模块不是由任何人了。我可以自己解决这些问题,但我不熟悉内部代码,而且我不喜欢他们的界面,因为它依赖于 amp 子类。因此,我写一个类似的替代品比尝试使用安瓿更有效率。

标签: python dynamic multiprocessing twisted


【解决方案1】:

您想要的功能是twisted.python.reflect.fullyQualifiedName几乎可以满足您的需求:

>>> from twisted.python.reflect import fullyQualifiedName
>>> fullyQualifiedName(fullyQualifiedName)
'twisted.python.reflect.fullyQualifiedName'

但是,在与静态方法交互时,它确实有所不足:

>>> class Something(object):
...     @staticmethod
...     def somethingElse():
...         pass
... 
>>> fullyQualifiedName(Something.somethingElse)
'__main__.somethingElse'

虽然这可以说是一个错误 - 我们可能会接受一个可以修复它的补丁:)。

反向操作是twisted.python.reflect.namedAny(之所以这么称呼是因为还有namedClassnamedModule等其他函数,但这会返回任何类型的东西):

>>> from twisted.python.reflect import namedAny
>>> namedAny(fullyQualifiedName(namedAny)) is namedAny
True

希望这会有所帮助!

【讨论】:

  • twisted.python.reflect.fullyQualifiedName
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-03-03
  • 1970-01-01
  • 2021-12-23
  • 1970-01-01
相关资源
最近更新 更多