如何通过Python导入C代码 [英] How to import C code through Python

查看:89
本文介绍了如何通过Python导入C代码的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试从python脚本导入交流代码。



我收到如下错误:

引用:

Traceback(最近一次调用最后一次):

文件function.py,第3行,< module>

hllDll = ctypes.WinDLL(someso.dll)

文件C:\Python35 \lib\ctypes\__init __。py,第347行, in __init__

self._handle = _dlopen(self._name,mode)

OSError:[WinError 193]%1不是有效的Win32应用程序





我的目标是在我的python脚本中使用myFunc函数。



我尝试了什么:



我创建了一个名为simple.c的文件,如下所示:

 int myFunc(int num)
{
if(num == 0)
return 0;
else
返回num;
}





我编译它来创建一个名为someso.so的共享对象



下面是我的python代码:

 import ctypes 
hllDll = ctypes.WinDLL(someso.dll)





我还尝试过ctypes的其他模块。

我有64位窗口和64位python应用程序。

解决方案

你创建了一个共享对象someso.so(不会在Windows中运行)但你正在尝试加载someso.dll。


我要感谢Richard MacCutchan的有用解决方案。使用它我想出了一种从python代码调用dll的方法。

1.首先,如果你的python应用程序是64位,你使用MingW创建的dll也应该是64位。因此请确保下载兼容版本的dll文件。

2.请不要创建共享对象并尝试导入它们,它不会工作。

共享对象是用于POSIX系统。如果你这样做,你将得到以下错误:



Quote:

Traceback (最近一次调用最后一次):

文件function.py,第3行,< module>

hllDll = ctypes.WinDLL(someso.dll)

文件C:\Python35 \ lib\ctypes\__init __。py,第347行,在__init__

self._handle = _dlopen(self._name ,模式)

OSError:[WinError 193]%1不是有效的Win32应用程序





可以说我们有一个在名为mydll.c的文件中的c程序下面:

 __ declspec(dllexport)int __cdecl Add(int a,int b)
{
return( a + b);
}



- ____ declspec(dllexport):这基本上允许我们指定存储类说明符。

- 这表示从dll文件导出函数或目标的编译器。

- 类似地还有另一个名为dllimport的存储类说明符,它告诉编译器

导出的对象可以在其他文件中导入。



注意:您可以根据您的python应用程序使用Mingw编译器,即32或64位。

您可以使用以下步骤进行编译:



 gcc -c mydll.c 
gcc -o basicDLL.dll -s -shared mydll.o -Wl, - 子系​​统,windows
python basicApplication.py
python basicApplication.py





让我们看看上面命令中使用的标志进行编译:

-Wl:跟随此标志的所有内容都作为参数传递给链接器。

最终将成为链接器调用如下:

ld --subsystem w indows

基本上这个调用将指示链接器将PE头子系统类型设置为windows。

这将指示将创建一个使用mingw编译的dll并且在windows中运行。



让我们看一下python端代码:

来自ctypes import * 
lib = CDLL('basicDLL')
print(lib.Add(1,2))





名称文件到任何东西让我们说basicApplication.py然后运行它。

输出为3



请注意:在dll中进行任何更改,将不得不重建。这意味着你首先编译.c文件,然后从中生成一个dll。



ctypes是一个非常有用的扩展c和python功能的模块其他


I am trying to import a c code from a python script.

I get an error as below:

Quote:

Traceback (most recent call last):
File "function.py", line 3, in <module>
hllDll = ctypes.WinDLL ("someso.dll")
File "C:\Python35\lib\ctypes\__init__.py", line 347, in __init__
self._handle = _dlopen(self._name, mode)
OSError: [WinError 193] %1 is not a valid Win32 application



My aim is to use the function "myFunc" into my python script.

What I have tried:

I created a file named : "simple.c" as below:

int myFunc(int num)
{
  if (num == 0)
    return 0;
  else
    return num;
}



I compiled it to create a shared object named "someso.so"

Below is my python code:

import ctypes
hllDll = ctypes.WinDLL ("someso.dll")



I have also tried other modules from ctypes.
I have a 64 bit windows and 64 bit python application.

解决方案

You have create a shared object someso.so (which will not run in Windows) but you are trying to load someso.dll.


I would like to thank Richard MacCutchan for his helpful solution. Using that i figured out a way to call dlls from python code.
1. Firstly if your python application is 64 bit, the dll which you create using MingW should also be 64 bit. so make sure to download a compatible version of the dll file.
2. Please do not create shared objects and try to import them, it wont work.
Shared objects are used in POSIX systems. If you do so you will get the below error:

Quote:

Traceback (most recent call last):
File "function.py", line 3, in <module>
hllDll = ctypes.WinDLL ("someso.dll")
File "C:\Python35\lib\ctypes\__init__.py", line 347, in __init__
self._handle = _dlopen(self._name, mode)
OSError: [WinError 193] %1 is not a valid Win32 application



Lets say we have a below c program in a file called mydll.c:

__declspec(dllexport) int __cdecl Add(int a, int b)
{
  return (a + b);
}


- ____declspec(dllexport): This basically allows us to specify a storage class specifier.
- This indicates to the compiler that a function or an objecy is being exported from a dll file.
- Similarly there is another storage class specifier called dllimport, this tells the compiler that the
exported object can be imported in an other file.

Note: You can use a Mingw compiler as per your python application i.e 32 or 64 bit.
You can compile using below steps:

gcc -c mydll.c
gcc -o basicDLL.dll -s -shared mydll.o -Wl,--subsystem,windows
python basicApplication.py
python basicApplication.py



Lets look at the flags used in the above commands for compilation:
-Wl: All which follow this flag are passed as an argument to the linker.
This eventually will become a linker call as below:
ld --subsystem windows
Basically this call will instruct the linker to set PE header subsystem type to windows.
This will indicate that a dll is to be created which is compiled using mingw and is to be run in windows.

Lets look at the python side code:

from ctypes import *
lib = CDLL('basicDLL')
print (lib.Add(1,2))



Name that file to anything lets say basicApplication.py and lets run it.
The output is 3

Please note: Making any changes in the dll, will have to be rebuilt again. Which means you first compile the .c file and then generate a dll out of it.

ctypes is a module which is very helpful to extend c and python functionalities with each other.


这篇关于如何通过Python导入C代码的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆