2017-02-02 8 views
0

문제가있어서 솔루션을 찾는 데 도움이 필요합니다. 나는 현재 내가 파이썬 C++에서 여러 변수를 보낼 PyBind11를 사용하기 위해 노력하고있어PYBIND11_PLUGIN 이미 본체가 있습니다

을하고 있어요 (다음 SQL 데이터를 기록하는 데 사용됩니다,하지만 그 점 외에입니다) 어떤

.

SQL_Service.cpp :

namespace py = pybind11; 
PYBIND11_PLUGIN(sqlserv) 
{ 
    py::module m("sqlserv", "pybind11 sql plugin"); 

    m.attr("bet_player") = BET_PLAYER; 
    m.attr("total_winnings") = TOTAL_WINNINGS; 

    return m.ptr(); 
} 

py::object import(const std::string& module, const std::string& path, py::object& globals) 
{ 
    py::dict locals; 
    locals["module_name"] = py::cast(module); 
    locals["path"] = py::cast(path); 

    py::eval<py::eval_statements>(
     "import imp\n" 
     "new_module = imp.load_module(module_name, open(path), path, ('py', 'U', imp.PY_SOURCE))\n", 
     globals, 
     locals); 

    return locals["new_module"]; 
} 

int SQL_Service::Log_SQL() 
{ 
    try 
    { 
     Py_Initialize(); 
     pybind11_init(); 

     py::object main = py::module::import("__main__"); 
     py::object globals = main.attr("__dict__"); 
     py::object module = import("sqlserv", "py_sql_service.py", globals); //name of the python file used 

     return 0; 
    } 
    catch (const py::error_already_set&) 
    { 
     std::cerr << ">>> Error! Uncaught exception:\n"; 
     PyErr_Print(); 
     return 1; 
    } 

} 

이 모두 잘 괜찮, 나는 파이썬으로 두 변수 (bet_player 및 total_winnings)를 얻을 수이고 나는 다음과 같은 프로세스를 사용하여이 작업을 수행입니다 그들을 처리하십시오.

다른 변수를 사용하고 다른 파이썬 스크립트와 관련된 다른 "PYBIND11_PLUGIN (somethingelse)"을 만들고 싶습니다.

다른 PYBIND11_PLUGIN을 정의하려고 할 때 문제가 발생합니다. 즉 :

내가 달성하기 위해 바라고 무엇
namespace py = pybind11; 
PYBIND11_PLUGIN(sqlserv) 
{ 
    py::module m("sqlserv", "pybind11 sql plugin"); 

    m.attr("bet_player") = BET_PLAYER; 
    m.attr("total_winnings") = TOTAL_WINNINGS; 

    return m.ptr(); 
} 
PYBIND11_PLUGIN(somethingelse) 
{ 
    py::module m("somethingelse", "pybind11 sql plugin"); 

    m.attr("bet_player2") = BET_PLAYER2; 
    m.attr("total_winning2s") = TOTAL_WINNINGS2; 

    return m.ptr(); 
} 


//This gives me the following error 
Error C2084 function 'PyObject *pybind11_init(void)' already has a body 

내 프로그램의 다른 곳에서 데이터를 수신 할 다양한 기능을 패키지화 보낼를 정의하는 내 수업 (SQL_Service)를 사용할

각각 다른 파이썬 스크립트에 필요한 데이터 만 가져옵니다. (아래 전체 예에서 Process_Baccarat (...) {...} 참조). 나는 코드의 작은 조각을주고, 또는 그 PyBind와 함께 일을 약간 다른 방식을 보여 다양한 자습서에 의존

날 일인가 무슨

. 따라서, 나는 내가 원하는 것을 정확히 얻는 법을 정말로 모른다.

네임 스페이스가 확실하지 않거나 그 중 2 개를 가질 수 없습니다. 아마도이 문제를 완전히 해결하는 또 다른 방법이 있습니다.

전역 변수를 사용하는 것에 대해 너무 행복하지 않습니다. (다시 말하면 일부 네임 스페이스 혼동이 있습니다.) 그래서 이것이 모두 멋지게 포장 될 수있는 방법이 있다면, 제가 찾고있는 것입니다. 작업 예제 코드는 크게 감사하겠습니다.

여기 참조를 위해 내 전체 (작업) SQL_Service.cpp 파일입니다 :

#include "SQL_Service.hpp" 

#include "Pybind\include\pybind11\pybind11.h" 
#include "Pybind\include\pybind11\eval.h" 

#include <string> 
#include <iostream> 


//G_VARS 
int BET_PLAYER = 0; 
int TOTAL_WINNINGS = 0; 


SQL_Service::SQL_Service() 
{ 

} 

SQL_Service::~SQL_Service() 
{ 

} 

namespace py = pybind11; 
PYBIND11_PLUGIN(sqlserv) 
{ 
    py::module m("sqlserv", "pybind11 sql plugin"); 

    m.attr("bet_player") = BET_PLAYER; 
    m.attr("total_winnings") = TOTAL_WINNINGS; 

    return m.ptr(); 
} 


py::object import(const std::string& module, const std::string& path, py::object& globals) 
{ 
    py::dict locals; 
    locals["module_name"] = py::cast(module); 
    locals["path"] = py::cast(path); 

    py::eval<py::eval_statements>(
     "import imp\n" 
     "new_module = imp.load_module(module_name, open(path), path, ('py', 'U', imp.PY_SOURCE))\n", 
     globals, 
     locals); 

    return locals["new_module"]; 
} 

//I Want to make all sorts of different kinds of these functions. 
void SQL_Service::Process_Baccarat(int bet_player, int total_winnings) 
{ 
    BET_PLAYER = bet_player; 
    TOTAL_WINNINGS = total_winnings; 

    Log_SQL(); 
} 

//And more of these too, if needed. 
int SQL_Service::Log_SQL() 
{ 
    try 
    { 
     Py_Initialize(); 
     pybind11_init(); 

     py::object main = py::module::import("__main__"); 
     py::object globals = main.attr("__dict__"); 
     py::object module = import("sqlserv", "py_sql_service.py", globals); //name of the python file used 

     return 0; 
    } 
    catch (const py::error_already_set&) 
    { 
     std::cerr << ">>> Error! Uncaught exception:\n"; 
     PyErr_Print(); 
     return 1; 
    } 

} 

답변

0

당신은 별도의 컴파일 단위에서 PYBIND11_PLUGIN을 넣어해야합니다. 귀하의 경우에는 코드를 sqlserv.cppsomethingelse.cpp 사이에서 분리하는 것이 좋습니다.

그러나 이것이 최선의 해결책인지 잘 모르겠습니다. 어쩌면 동일한 모듈 내에서 정적 멤버가있는 서로 다른 클래스가 있을까요?