Как python может запустить многопроцессорное создание без __main__ - PullRequest
1 голос
/ 22 марта 2020

Я расширяю свою c программу некоторым фрагментом python кода (сначала python env в c, затем импортирую функцию из python модуля и запускаю ее), в какой ситуации мне пришлось Вызовите многопроцессорный модуль и порождайте процесс без функции __main__, я знаю, что он работал в __main__, но могу ли я что-то сделать в моей программе C и сделать возможным запуск многопроцессорного вызова вне __main __.

файл x. c

#include <Python.h>
#include <iostream>


using namespace std;

int main()
{
    Py_Initialize();
    PyObject *module_name = PyUnicode_FromString("t1");
    PyRun_SimpleString("import sys");
    PyRun_SimpleString("sys.path.append(\"./\")");
    cout << "Python Version: " << endl << Py_GetVersion() << endl << endl;
    PyObject *module = PyImport_Import(module_name);
    PyObject *func = PyObject_GetAttrString(module, "run");
    PyObject *args = Py_BuildValue("()");
    PyObject_CallObject(func, args);
    Py_DECREF(args);
    Py_DECREF(func);
    Py_DECREF(module);
    Py_DECREF(module_name);
    return 0;
}
  • Makefile *
all:
    g++ -O0 -g3 -std=c++11 x.c $(shell python3-config --includes) $(shell python3-config --ldflags) -o a.out -Wall

файл t1.py

# -*- coding: utf-8 -*-

import multiprocessing as mp


def test():
    print("hello world")



def run():
    ctx = mp.get_context('spawn')
    # ctx = mp.get_context('fork')
    p = ctx.Process(target=test, args=())
    p.start()
    p.join()

# run()

вызов функции run из x. c ничего не печатает, а добавление run () в конце t1.py и выполнение напрямую с python3 t1.py вызовет ошибку 'freeze_support'.

t2.py

# -*- coding: utf-8 -*-

import multiprocessing as mp


def test():
    print("hello world")



def run():
    # ctx = mp.get_context('spawn')
    ctx = mp.get_context('fork')
    p = ctx.Process(target=test, args=())
    p.start()
    p.join()

Этот скрипт может напечатать мир приветствия при вызове функции run из x. c

t3. py

# -*- coding: utf-8 -*-

import multiprocessing as mp


def test():
    print("hello world")



def run():
    ctx = mp.get_context('spawn')
    # ctx = mp.get_context('fork')
    p = ctx.Process(target=test, args=())
    p.start()
    p.join()


if __name__ == "__main__":
    run()

Этот скрипт работает отдельно (python3 .5 t3.py) также работает (распечатать привет мир в конце)

Я хочу выполнить r Функция un без записи __main__ в программе c (через PyObject_CallObject), затем, как я могу заставить ее работать.

1 Ответ

0 голосов
/ 23 марта 2020

В конце раздела Контексты и методы запуска следующее предупреждение:

Предупреждение: Методы запуска 'spawn' и 'forkserver' в настоящее время не может использоваться с «замороженными» исполняемыми файлами (т. е. двоичными файлами, создаваемыми пакетами, такими как PyInstaller и cx_Freeze ) в Unix. Метод запуска 'fork' работает.

Поскольку multiprocessing создает новый процесс внутри текущего, который запускает скомпилированный (то есть замороженный) исполняемый файл, невозможно использовать 'spawn' в качестве метода запуска.

Вы можете продолжать использовать 'fork', однако (как вы описали, это работает для вашего примера).

...