MRo*_*lin 7 python conda python-multiprocessing
我有两个版本的Python(这些实际上是两个conda环境)
/path/to/bin-1/python
/path/to/bin-2/python
Run Code Online (Sandbox Code Playgroud)
从一个版本的python我想要使用像multiprocessing.Process对象之类的东西启动一个在另一个版本中运行的函数.事实证明,这是可行的使用set_executable方法:
ctx = multiprocess.get_context('spawn')
ctx.set_executable('/path/to/bin-2/python')
Run Code Online (Sandbox Code Playgroud)
事实上,我们可以看到这实际上是使用该可执行文件启动的:
def f(q):
import sys
q.put(sys.executable)
if __name__ == '__main__':
import multiprocessing
ctx = multiprocessing.get_context('spawn')
ctx.set_executable('/path/to/bin-2/python')
q = ctx.Queue()
proc = ctx.Process(target=f, args=(q,))
proc.start()
print(q.get())
$ python foo.py
/path/to/bin-2/python
Run Code Online (Sandbox Code Playgroud)
但是,当我做同样的事情,sys.path而不是sys.executable我发现托管python进程的sys.path打印出来,而不是我会发现/path/to/bin-2/python -c "import sys; print(sys.path)"直接运行的sys.path .
如果我使用fork,我习惯了这种事情.我本来希望我的'spawn'行为与从shell中输入python解释器一样.
是否可以使用多处理库来运行函数,并使用其他Python可执行文件中的队列以及从shell启动它时所具有的环境?
更广泛地说,如何填充sys.path以及以这种方式使用多处理和直接启动解释器之间有什么不同?
小智 3
我遇到了同样的问题。我的系统范围的 Python 可执行文件位于/path/to/bin-1/python,并且我使用virtualenv包含另一个 Python 可执行文件的虚拟环境创建了一个虚拟环境/path/to/bin-2/python。为了为所需的生成进程设置正确的路径/环境,我最终将文件夹中的/path/to/bin-2/python代码复制到.activate_this.pyvirtualenvf(q)
def f(q):
import sys, os
def active_virtualenv(exec_path):
"""
copy virtualenv's activate_this.py
exec_path: the python.exe path from sys.executable
"""
# set env. var. PATH
old_os_path = os.environ.get('PATH', '')
os.environ['PATH'] = os.path.dirname(os.path.abspath(exec_path)) + os.pathsep + old_os_path
base = os.path.dirname(os.path.dirname(os.path.abspath(exec_path)))
# site-pachages path
if sys.platform == 'win32':
site_packages = os.path.join(base, 'Lib', 'site-packages')
else:
site_packages = os.path.join(base, 'lib', 'python%s' % sys.version[:3], 'site-packages')
# modify sys.path
prev_sys_path = list(sys.path)
import site
site.addsitedir(site_packages)
sys.real_prefix = sys.prefix
sys.prefix = base
# Move the added items to the front of the path:
new_sys_path = []
for item in list(sys.path):
if item not in prev_sys_path:
new_sys_path.append(item)
sys.path.remove(item)
sys.path[:0] = new_sys_path
return None
active_virtualenv(sys.executable)
q.put(sys.executable)
# check some unique package in this env.
import special_package
print "package version: {}".format(special_package.__version__)
if __name__ == '__main__':
import multiprocessing
multiprocessing.set_executable('/path/to/bin-2/python')
q = multiprocessing.Queue()
proc = multiprocessing.Process(target=f, args=(q,))
proc.start()
proc.join()
print(q.get())
Run Code Online (Sandbox Code Playgroud)
标准输出:
$ python foo.py
/path/to/bin-2/python
package version: unique_version_only_in_virtualenv
Run Code Online (Sandbox Code Playgroud)
我不太确定的一件事是sys和之前os是imported active_virtualenv(),这意味着它们来自系统范围的 Python 环境。但我需要的其他包f(q)来自虚拟环境。也许在切换环境后值得重新使用import它们。
| 归档时间: |
|
| 查看次数: |
751 次 |
| 最近记录: |