简体   繁体   English

Python嵌入C ++

[英]Python Embedded in C++

So I have a GUI program that has a great deal of "stuff" going on. 因此,我有一个GUI程序,正在进行很多“工作”。 I am adding a python scripting interface so someone can interact problematically with this environment. 我正在添加python脚本接口,以便有人可以与此环境进行有问题的交互。 I am using boost python. 我正在使用boost python。 So first thing I have is a new module I want to create. 首先,我要创建一个新模块。 For simplicity right now my module just is hello world... 为了简单起见,我的模块现在是世界。

#include <boost/python.hpp>                                                     

char const* greet() {                                                           
   return "hello, world" ;                                                      
}                                                                               

BOOST_PYTHON_MODULE(cerrnimapi) {                                               
  boost::python::def( "greet", greet ) ;                                        
}  

In my system I have a class that looks like this... 在我的系统中,我有一个看起来像这样的类...

Controller::Controller( ) {         
  Py_Initialize( ) ;                                                            

  main_module = boost::python::import( "__main__" ) ;                           
  main_namespace = main_module.attr( "__dict__" ) ;                             
}                                                                                                                                                     

void Controller::execute_script( std::string filename ) {                       
  try {                                                                         
    boost::python::api::object ignored =                                        
      boost::python::exec_file( filename.c_str(), main_namespace ) ;            
  } catch( boost::python::error_already_set const & ) {                         
    if (PyErr_ExceptionMatches(PyExc_ZeroDivisionError)) {                      
    } else {                                                                    
        PyErr_Print();                                                          
    }                                                                           
  }                                                                             
}

Now when I go to execute the script in the GUI I get an error... 现在,当我在GUI中执行脚本时,出现错误...

Traceback (most recent call last):
  File "/home/mokon/repository/trunk/python.py", line 1, in <module>
    import cerrnimapi
ImportError: No module named cerrnimapi

So of course I am building something wrong. 因此,我当然会犯错。 My build system uses autotools so here are a few pieces of that build system that relate to this... 我的构建系统使用自动工具,因此这里有一些与此相关的构建系统...

In configure.ac: 在configure.ac中:

AM_PATH_PYTHON                                                                  
AC_ARG_VAR([PYTHON_INCLUDE], [Include flags for python, bypassing python-config])
AC_ARG_VAR([PYTHON_CONFIG], [Path to python-config])                            
AS_IF([test -z "$PYTHON_INCLUDE"], [                                            
  AS_IF([test -z "$PYTHON_CONFIG"], [                                           
    AC_PATH_PROGS([PYTHON_CONFIG],                                              
                  [python$PYTHON_VERSION-config python-config],                 
                  [no],                                                         
                  [`dirname $PYTHON`])                                          
    AS_IF([test "$PYTHON_CONFIG" = no], [AC_MSG_ERROR([cannot find python-config for $PYTHON.])])
  ])                                                                            
  AC_MSG_CHECKING([python include flags])                                       
  PYTHON_INCLUDE=`$PYTHON_CONFIG --includes`                                    
  AC_MSG_RESULT([$PYTHON_INCLUDE])                                              
])                                                                              

AC_ARG_VAR([PYTHON_LD], [Linker flags for python, bypassing python-config])     
AS_IF([test -z "$PYTHON_LD"], [                                                 
  AS_IF([test -z "$PYTHON_CONFIG"], [                                           
    AC_PATH_PROGS([PYTHON_CONFIG],                                              
                  [python$PYTHON_VERSION-config python-config],                 
                  [no],                                                         
                  [`dirname $PYTHON`])                                          
    AS_IF([test "$PYTHON_CONFIG" = no], [AC_MSG_ERROR([cannot find python-config for $PYTHON.])])
  ])                                                                            
  AC_MSG_CHECKING([python linker flags])                                        
  PYTHON_LD=`$PYTHON_CONFIG --ldflags`                                          
  AC_MSG_RESULT([$PYTHON_LD])                                                   
]) 

In my obj/ dir Makefile.am... 在我的obj / dir Makefile.am中...

pyexec_LTLIBRARIES = cerrnimapi.la                                              
cerrnimapi_la_SOURCES = ${SRC_DIR}/lib/PythonAPI.cpp                            
cerrnimapi_la_LDFLAGS = -avoid-version -module $(PYTHON_LD)                     
cerrnimapi_la_CXXFLAGS = $(PYTHON_INCLUDE)  

My makefile builds the shared lib and its in the obj folder along with my main program. 我的makefile与我的主程序一起在obj文件夹中构建共享库及其共享库。 This doesn't help. 这没有帮助。 I have also done a make install to install the cerrnimapi lib in the python folders. 我还进行了make install,将cerrnimapi lib安装在python文件夹中。 This doesn't help. 这没有帮助。

I have also tried adding the PythonAPI.cpp to my main programs SOURCES but to no avail. 我也曾尝试将PythonAPI.cpp添加到我的主程序SOURCES中,但无济于事。

Any ideas? 有任何想法吗? let me know what additional information would be helpful. 让我知道哪些其他信息会有所帮助。

Some things to check: 要检查的一些事情:

  • Run nm over your .so file (which might be in .libs ) to make sure your module init func is exported. 在.so文件(可能在.libs )上运行nm ,以确保导出了模块初始化函数。
  • Make your program print out the value of sys.path (use PyRun_SimpleString) to see where it's expecting your module to turn up. 使您的程序打印出sys.path的值(使用PyRun_SimpleString)以查看期望模块打开的位置。 If you're defining modules for your interpreter only, you probably don't want to install them in $pyexecdir . 如果仅为解释器定义模块,则可能不想在$pyexecdir安装它们。
  • Read the Extending Embedded Python article. 阅读扩展嵌入式Python文章。 You don't really need to build dynamic libraries at all, unless you're trying for a plugin architecture. 除非您正在尝试使用插件体系结构,否则根本不需要构建动态库。

A point on style: You should try and find $PYTHON_CONFIG outside of your tests for $PYTHON_INCLUDE and $PYTHON_LD so you're not doing the AC_PATH_PROGS twice: 风格上的要点:您应该在$PYTHON_INCLUDE$PYTHON_LD测试之外尝试找到$PYTHON_CONFIG ,这样就不必AC_PATH_PROGS两次AC_PATH_PROGS了:

AM_PATH_PYTHON                                                                  
AC_ARG_VAR([PYTHON_CONFIG], [Path to python-config])                            
AS_IF([test -z "$PYTHON_CONFIG"], [                                           
  AC_PATH_PROGS([PYTHON_CONFIG],                                              
                [python$PYTHON_VERSION-config python-config],                 
                [no],                                                         
                [`dirname $PYTHON`])                                          
])                                                                            

AC_ARG_VAR([PYTHON_INCLUDE], [Include flags for python, bypassing python-config])
AS_IF([test -z "$PYTHON_INCLUDE"], [                                            
  AC_MSG_CHECKING([python include flags])                                       
  AS_IF([test "$PYTHON_CONFIG" = no], [AC_MSG_ERROR([cannot find python-config for $PYTHON.])])
  PYTHON_INCLUDE=`$PYTHON_CONFIG --includes`                                    
  AC_MSG_RESULT([$PYTHON_INCLUDE])                                              
])                                                                              

AC_ARG_VAR([PYTHON_LD], [Linker flags for python, bypassing python-config])     
AS_IF([test -z "$PYTHON_LD"], [                                                 
  AC_MSG_CHECKING([python linker flags])                                        
  AS_IF([test "$PYTHON_CONFIG" = no], [AC_MSG_ERROR([cannot find python-config for $PYTHON.])])
  PYTHON_LD=`$PYTHON_CONFIG --ldflags`                                          
  AC_MSG_RESULT([$PYTHON_LD])                                                   
])

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM