2009-06-02 226 views
10

我使用boost :: python将一些python代码嵌入到应用程序中。我能够正确评估打印语句或其他表达式,但是当我尝试导入模块时,它不是导入并且应用程序正在退出。此外,嵌入式代码中的globals()函数调用也会产生运行时错误。如何在boost :: python嵌入式Python代码中导入模块?

#include <boost/python.hpp> 

using namespace boost; 
using namespace boost::python; 
using namespace boost::python::api; 

int main(void) { 
    Py_Initialize(); 
    object main_module = import("__main__"); 
    object main_namespace = main_module.attr("__dict__"); 
    main_namespace["urllib2"] = import("urllib2"); 

    object ignored = exec(
      "print 'time'\n", main_namespace); 
} 

这里,我试图导入的urllib2使用升压导入功能,这个编译和运行正常,但有以下exec语句,它给出了一个错误。

object ignored = exec(
      "print urllib2\n" 
      "print 'time'\n", main_namespace); 

或者当我删除boost导入函数并从嵌入代码中进行导入时,它也会报错。我尝试使用一个尝试:除了:块,但也不起作用。这是因为C++应用程序无法找到urllib2 py模块的位置?有没有办法在尝试导入之前设置模块的路径?

这是为内部使用而构建的,因此某些路径的硬编码是可以接受的。

编辑:更多信息:
这就是发生了什么事。我做了一个try ... catch,并在有任何异常时调用PyErr_Print(),并且在有模块导入甚至函数调用时,始终将此视为错误。错误信息:

Traceback (most recent call last): 
    File "<string>", line 1, in <module> 
TypeError: 'NoneType' object does not support item assignment 

任何人都可以想到任何原因吗?

回答

3

这没有帮助,但我发现了一个不同的解决方案,我的问题。我当前的代码如下所示:

#include <boost/python.hpp> 
#include <iostream> 

using namespace std; 
using namespace boost; 
using namespace boost::python; 
using namespace boost::python::api; 

int main(void) { 
     Py_Initialize(); 
     boost::python::object http = boost::python::import("urllib2"); 

     try 
     { 
       boost::python::object response = http.attr("urlopen")("http://www.google.com"); 
       boost::python::object read = response.attr("read")(); 
       std::string strResponse = boost::python::extract<string>(read); 
       cout << strResponse << endl; 
     } 
     catch(...) 
     { 
       PyErr_Print(); 
       PyErr_Clear(); 
     } 
} 

不管怎么说,谢谢你的答案乔纳斯

4

如果你还没有,你需要

 
import sys 
sys.path.append("/home/user/whatever") 

这嵌入的boost ::蟒(Python的V2.5)当几年前花了我的问题护理。

编辑:

在旧代码中捅了一圈。也许,这是卓有成效的:

 
Py_SetProgramName(argv[0]); 
Py_InitializeEx(0); 

听起来不确定,你应该真正需要的Py_SetProgramName(),但我依稀记得一些可疑的商业存在。

+0

感谢您的回应,并且真的是为了延迟尝试并告诉您,Jonas。 我试过了,但这没有帮助。如果它有这个单一语句“print globals()\ n”,我甚至无法让程序运行。我在Windows和Linux上尝试了相同的代码,并且在任何地方都有相同的响应。 我正在使用Boost 1.39.0 – Sahas 2009-06-07 05:25:01

+0

糟糕。我没有注意到编辑。我也会尝试。 – Sahas 2009-06-16 04:51:52

0

我遇到同样的问题,因为你,IEA很简单的例子导致类型错误,并找到了答案在this question,即提供名称空间两次,包括全局和本地。