python中怎么调用另一个程序

python中怎么调用另一个程序,第1张

python中怎么调用另一个程序?

1、自身函数调用:

    自身函数的调用时相当方便的,在定义好了函数以后直接按定义的格式调用即可,出现的错误为参数数量不匹配,如:TypeError: func() missing 1 required positional argument: 's',意思为func()函数有一个形式参时但是没有传入相对应的实参值。

2、通过包或模块调用:

通过包或模块调用相对自身函数调用比较复杂,需要提前导入包或模块,常用的方法为import 或者from import,导入成功的前提是对应的包或模块在python路径之下,可以通过sys.path(sys为系统内置模块可以直接使用import sys导入)来查看python路径。以导入第三方包文件requests为例。

3、通过类方法调用:

通过类方法的调用需要在调用之前,实例化一个类对象,通过这个类对象来调用类方法,

注意第三个方法为私有方法,不允许类外部访问。

二、Python调用C/C++

1、Python调用C动态链接库

Python调用C库比较简单,不经过任何封装打包成so,再使用python的ctypes调用即可。

(1)C语言文件:pycall.c

[html] view plain copy

/***gcc -o libpycall.so -shared -fPIC pycall.c*/

#include <stdio.h>

#include <stdlib.h>

int foo(int a, int b)

{

printf("you input %d and %d\n", a, b)

return a+b

}

(2)gcc编译生成动态库libpycall.so:gcc -o libpycall.so -shared -fPIC pycall.c。使用g++编译生成C动态库的代码中的函数或者方法时,需要使用extern "C"来进行编译。

(3)Python调用动态库的文件:pycall.py

[html] view plain copy

import ctypes

ll = ctypes.cdll.LoadLibrary

lib = ll("./libpycall.so")

lib.foo(1, 3)

print '***finish***'

(4)运行结果:

2、Python调用C++(类)动态链接库

需要extern "C"来辅助,也就是说还是只能调用C函数,不能直接调用方法,但是能解析C++方法。不是用extern "C",构建后的动态链接库没有这些函数的符号表。

(1)C++类文件:pycallclass.cpp

[html] view plain copy

#include <iostream>

using namespace std

class TestLib

{

public:

void display()

void display(int a)

}

void TestLib::display() {

cout<<"First display"<<endl

}

void TestLib::display(int a) {

cout<<"Second display:"<<a<<endl

}

extern "C" {

TestLib obj

void display() {

obj.display()

}

void display_int() {

obj.display(2)

}

}

(2)g++编译生成动态库libpycall.so:g++ -o libpycallclass.so -shared -fPIC pycallclass.cpp。

(3)Python调用动态库的文件:pycallclass.py

[html] view plain copy

import ctypes

so = ctypes.cdll.LoadLibrary

lib = so("./libpycallclass.so")

print 'display()'

lib.display()

print 'display(100)'

lib.display_int(100)

(4)运行结果:

3、Python调用C/C++可执行程序

(1)C/C++程序:main.cpp

[html] view plain copy

#include <iostream>

using namespace std

int test()

{

int a = 10, b = 5

return a+b

}

int main()

{

cout<<"---begin---"<<endl

int num = test()

cout<<"num="<<num<<endl

cout<<"---end---"<<endl

}

(2)编译成二进制可执行文件:g++ -o testmain main.cpp。

(3)Python调用程序:main.py

[html] view plain copy

import commands

import os

main = "./testmain"

if os.path.exists(main):

rc, out = commands.getstatusoutput(main)

print 'rc = %d, \nout = %s' % (rc, out)

print '*'*10

f = os.popen(main)

data = f.readlines()

f.close()

print data

print '*'*10

os.system(main)

(4)运行结果:

4、扩展Python(C++为Python编写扩展模块)

所有能被整合或导入到其它python脚本的代码,都可以被称为扩展。可以用Python来写扩展,也可以用C和C++之类的编译型的语言来写扩展。Python在设计之初就考虑到要让模块的导入机制足够抽象。抽象到让使用模块的代码无法了解到模块的具体实现细节。Python的可扩展性具有的优点:方便为语言增加新功能、具有可定制性、代码可以实现复用等。

为 Python 创建扩展需要三个主要的步骤:创建应用程序代码、利用样板来包装代码和编译与测试。

(1)创建应用程序代码

[html] view plain copy

#include <stdio.h>

#include <stdlib.h>

#include <string.h>

int fac(int n)

{

if (n <2) return(1)/* 0! == 1! == 1 */

return (n)*fac(n-1)/* n! == n*(n-1)! */

}

char *reverse(char *s)

{

register char t,/* tmp */

*p = s, /* fwd */

*q = (s + (strlen(s) - 1))/* bwd */

while (p <q) /* if p <q */

{

t = *p/* swap &move ptrs */

*p++ = *q

*q-- = t

}

return(s)

}

int main()

{

char s[BUFSIZ]

printf("4! == %d\n", fac(4))

printf("8! == %d\n", fac(8))

printf("12! == %d\n", fac(12))

strcpy(s, "abcdef")

printf("reversing 'abcdef', we get '%s'\n", \

reverse(s))

strcpy(s, "madam")

printf("reversing 'madam', we get '%s'\n", \

reverse(s))

return 0

}

上述代码中有两个函数,一个是递归求阶乘的函数fac();另一个reverse()函数实现了一个简单的字符串反转算法,其主要目的是修改传入的字符串,使其内容完全反转,但不需要申请内存后反着复制的方法。

(2)用样板来包装代码

接口的代码被称为“样板”代码,它是应用程序代码与Python解释器之间进行交互所必不可少的一部分。样板主要分为4步:a、包含Python的头文件;b、为每个模块的每一个函数增加一个型如PyObject* Module_func()的包装函数;c、为每个模块增加一个型如PyMethodDef ModuleMethods[]的数组;d、增加模块初始化函数void initModule()。


欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/yw/8033147.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-04-12
下一篇 2023-04-12

发表评论

登录后才能评论

评论列表(0条)

保存