Python调用C/Fortran混合的动态链接库--中篇
接下来,介绍一个简单的例子,从fortran中传递并返回一维自定义结构体数组到python
注意点:
1、fortran新标准支持可分配数组作为变量传入并在subroutine或function分配后返回;
2、BIND不支持传入可分配数组(也即1和2无法同时使用);
3、fortran没有垃圾自动回收机制;
综合上述3点,利用ctypes调用fortran不能也不宜直接返回形状大小在计算前无法确定的数组,折衷的办法是:
a、估算出返回数组的大小,可以适当偏大;
b、在fortran的module定义全局可分配数组,第一次调用后存储结果并返回数组形状数值,在python中利用numpy开辟空数组,再次调用fortran得到结果并清空fortran中module的全局变量
fortran代码:
module sam
use,intrinsic::iso_c_binding
implicit none
type,bind(C)::abc
!Define struct
character(len=)::nam
real(c_float)::val()
end type
! Global variable in fortran module
! Notice: dealloacte after using to avoid memory leak
type(abc),allocatable::stu(:)
contains
subroutine calc(input,output,n1)bind(c,name='ex01')
! Example
! Both in and out variables has assumed shape
! Bind(C) not allowed pass alloctable variables
! Pure Fortran2008 allows pass alloctable array to subroutine to allocate or deallocate
implicit none
integer(c_int),intent(in),value::n1
real(c_float),intent(in)::input(n1)
type(abc),intent(out)::output(*n1) integer::i do i=,size(output)
output(i)%nam = "abcdefea"
output(i)%val(:) = real(i-,)
output(i)%val(::) = i*2.5E0
enddo
return
end subroutine subroutine calc2(input,n1,n2)bind(c,name='ex02_1')
! Example 02_1
! Return result's shape
implicit none
integer(c_int),intent(in),value::n1
real(c_float),intent(in)::input(n1)
integer(c_int),intent(out)::n2 integer::i,j call clear()
if(input()<.E0)then
allocate(stu())
else
allocate(stu(int(input())+))
endif
do i=,size(stu)
stu(i)%nam = "daefvdefefadfad"
do j=,size(stu(i)%val)
stu(i)%val(j) = i*j*1.5E0
enddo
enddo
n2 = size(stu)
return
end subroutine subroutine getdata(output,n)bind(c,name='ex02_2')
! Example 02_2
! Return result and do clear
implicit none
integer(c_int),intent(in),value::n
type(abc),intent(out)::output(n) output = stu
call clear()
return
end subroutine subroutine clear()
implicit none
if(allocated(stu))deallocate(stu)
end subroutine
end module program test
use sam
implicit none
real(c_float)::array()
type(abc)::student(*)
integer::i array = [.E0,.E0,.E0,.E0,.E0]
call calc(array,student,)
do i=,size(student)
write(*,*)student(i)%nam,student(i)%val
enddo
end program
python代码:
#! /usr/bin/env python
#coding=utf-8 '''
A short example of use ctypes and numpy to call fortran dynamic library
example for 1d struct array pass or access
'''
import numpy as np
from numpy.ctypeslib import load_library,ndpointer
from ctypes import c_int #define struct as same sa fortran
abc = np.dtype([("nam",'S80',1),("val",'f4',10)])
#load dynamic library
flib = load_library("libexample",".")
#function handle of ex01
fun01 = flib.ex01
#define input arguments
fun01.argtypes = [ndpointer('f4'),ndpointer(abc),c_int]
#
n1,n2 = 5,np.array(0,'i4')
vec = np.zeros((n1,),'f4')
student = np.empty((n1*2,),abc)
#print vec
fun01(vec,student,n1)
#print student
#function handle of ex02_1
fun02_1 = flib.ex02_1
fun02_1.argtypes = [ndpointer('f4'),c_int,ndpointer('i4')]
fun02_1(vec,n1,n2)
#print n1,n2
#function handle of ex02_2
fun02_2 = flib.ex02_2
fun02_2.argtypes = [ndpointer(abc),c_int]
student2 = np.empty((n2,),abc)
fun02_2(student2,n2)
print student2
编译命令:
gfortran test.f90 -fPIC -shared -o libexample.so
Python调用C/Fortran混合的动态链接库--中篇的更多相关文章
- Python调用C/Fortran混合的动态链接库--上篇
内容描述: 在32位或64位的windows或GNU/Linux系统下利用Python的ctypes和numpy模块调用C/Fortran混合编程的有限元数值计算程序 操作系统及编译环境: 32bit ...
- Python调用C/Fortran混合的动态链接库-下篇
接着前面的内容,我们在这里继续介绍Python传递二维数组到fortran并进行简单计算后返回的例子. 问题描述: module py2f90 use,intrinsic::iso_c_binding ...
- Python调用C的DLL(动态链接库)
开发环境:mingw64位,python3.6 64位 参考博客: mingw编译dll: https://blog.csdn.net/liyuanbhu/article/details/426123 ...
- Python调用DLL动态链接库——ctypes使用
最近要使用python调用C++编译生成的DLL动态链接库,因此学习了一下ctypes库的基本使用. ctypes是一个用于Python的外部函数库,它提供C兼容的数据类型,并允许在DLL或共享库中调 ...
- [转载:]C#与Fortran混合编程之本地调用Fortran动态链接库
前言 C#发展到现在,已是一门相当完善的语言,他基于C语言风格,演化于C++.并依靠强大的.NET底层框架.C#可以用来快速构建桌面及Web应用.然而在我们的实际工作中,尽管C#已经非常完善,但还是不 ...
- Python调用C/C++动态链接库
Python调用C/C++动态链接库 2013年07月26日 ⁄ 综合 ⁄ 共 3219字 ⁄ 字号 小 中 大 ⁄ 评论关闭 吐槽(可略过):不知不觉,4月份毕业,5月份进入团队,已有7个月.大 ...
- Python调用C/C++动态链接库的方法详解
Python调用C/C++动态链接库的方法详解 投稿:shichen2014 这篇文章主要介绍了Python调用C/C++动态链接库的方法,需要的朋友可以参考下 本文以实例讲解了Python调用C/C ...
- Python的扩展接口[2] -> 动态链接库DLL[1] -> 组件对象模型 COM 的 Python 调用
组件对象模型 COM 的 Python 调用 关于COM的基本概念,可参考组件对象模型 COM的内容,下面主要介绍两种使用 Python 调用 COM 组件的方法. 1 使用 win32com 1.1 ...
- python调用C/C++动态链接库和jython
总结(非原创) Python调用C库比较简单,不经过任何封装打包成so,再使用python的ctypes调用即可. 1. C语言文件:pycall.c #include <stdio.h> ...
随机推荐
- wordpress需要FTP用户名密码的问题
wordpress安装删除插件需要FTP用户名密码的问题 方法一: 服务器命令操作: 1.在wordpress目录下面wp-config.php末尾加入下面代码: if(is_admin()) { ...
- [android开发篇]使用系统权限流程
1 声明权限https://developer.android.com/training/permissions/declaring.html 每款 Android 应用都在访问受限的沙盒中运行.如果 ...
- zoj2112 主席树动态第k大 ( 参考资料链接)
参考链接: http://blog.csdn.net/acm_cxlove/article/details/8565309 http://www.cnblogs.com/Rlemon/archive/ ...
- 算法复习——无源汇可行流(zoj2314)
题目: The terrorist group leaded by a well known international terrorist Ben Bladen is buliding a nucl ...
- 刷题总结——谈笑风生(主席树+dfs序的应用)
题目: Description 设T 为一棵有根树,我们做如下的定义:• 设a和b为T 中的两个不同节点.如果a是b的祖先,那么称“a比b不知道高明到哪里去了”.• 设a 和 b 为 T 中的两个不同 ...
- P2015 二叉苹果树 (树形动规)
题目描述 有一棵苹果树,如果树枝有分叉,一定是分2叉(就是说没有只有1个儿子的结点) 这棵树共有N个结点(叶子点或者树枝分叉点),编号为1-N,树根编号一定是1. 我们用一根树枝两端连接的结点的编号来 ...
- 将list分成等数量
import java.util.ArrayList; import java.util.List; public class CollectionGroupUtil { public static ...
- BZOJ 1006 [HNOI2008]神奇的国度==最大势算法
神奇的国度 K国是一个热衷三角形的国度,连人的交往也只喜欢三角原则.他们认为三角关系:即AB相互认识,BC相互认识,CA相互认识,是简洁高效的.为了巩固三角关系,K国禁止四边关系,五边关系等等的存在. ...
- 【Vijos1412】多人背包(背包DP)
题意:求0/1背包的前K优解总和 k<=50 v<=5000 n<=200 思路:日常刷水 归并即可,不用排序 ; ..,..,..]of longint; w,c,a,b:..]o ...
- 关于错误Access Violation和too many consecutive exceptions 解决方法
关于错误Access Violation和too many consecutive exceptions 解决方法 “如果DLL中用到了DELPHI的string类型,则DLL和主程序中都需要加上Sh ...