Python F2py转换字符(*)分段错误
我正在尝试使用Fortran90数值模型和使用f2py的python3.5Python F2py转换字符(*)分段错误,python,arrays,fortran,character,f2py,Python,Arrays,Fortran,Character,F2py,我正在尝试使用Fortran90数值模型和使用f2py的python3.5 f2py -c module.f90 -m mod --fcompiler=gfortran 该模型是一个Fortran模块,包含变量、函数和子例程。我在这里发布了一个代码示例,它具有数值模型的所有特性 module modul implicit none integer :: inte real :: re integer, dimension(3) :: array CHARACTER(*), PARAMETER
f2py -c module.f90 -m mod --fcompiler=gfortran
该模型是一个Fortran模块,包含变量、函数和子例程。我在这里发布了一个代码示例,它具有数值模型的所有特性
module modul
implicit none
integer :: inte
real :: re
integer, dimension(3) :: array
CHARACTER(*), PARAMETER :: chara = "helloWorld"
contains
integer function fun()
fun = array(1) + array(2) + array(3)
end function
subroutine subrout(a,b)
real, intent(out) :: b
integer, intent(out) :: a
a = inte + fun()
b = re
write(*,*) chara
end subroutine subrout
end module modul
使用f2py对代码进行的转换工作正常,但是,当我用Python导入模块时,我收到了一个分段错误
>>> import mod
Segmentation fault (core dumped)
我意识到问题取决于字符数组的未指定维度
CHARACTER(*), PARAMETER :: chara = "helloWorld"
同样,如果我删除了这行代码,或者为数组指定了一个固定的维度(如字符(20)),那么该模块在Python中可以正常工作
1。有没有一种方法可以使它在不修改Fortran代码的情况下工作
(模型既长又复杂,如果可能的话,我不想
继续工作)?
System information:
OS: Ubuntu 16.04
Python 3.5.2
f2py Version: 2
numpy Version: 1.12.1
GNU Fortran (Ubuntu 5.4.0-6ubuntu1~16.04.4) 5.4.0 20160609
字符数组用于定义代码中的字符串(如错误消息)并处理文件的输入/输出。解决问题的一种方法(如果问题1没有答案)是为所有字符串定义一个固定的最大维度(即整数,参数::lenChar=100),然后使用
CHARACTER(lenChar), PARAMETER :: chara
而不是以前的声明。在本例中,模块在Python中成功导入,但当我尝试修改数组内容时,它需要输入lenChar long(其他类型的数组(如INTEGER或REAL)也会出现同样的问题,并且不依赖于PARAMETER属性)
您似乎混淆了可变长度字符串(不管它是什么,类似于Fortran 2003中的字符串)、字符串常量和伪参数,它们会占用您传递的长度。您可能想要:
subroutine sub(ch)
character(*), intent(in) :: ch
print *, ch
end
这与您的示例完全不同。这里的参数ch
将接受您传递到那里的任何长度的字符串
问题在于假定的长度字符常量。这足以触发错误
module m
CHARACTER(*), PARAMETER :: chara = "helloWorld"
end module m
这不是字符数组,而是假定长度的标量字符串
它与完全相等
module m
CHARACTER(10), PARAMETER :: chara = "helloWorld"
end module m
唯一的区别是,在前一种情况下,如果您懒得手动计算长度(或者您经常更改长度),编译器会自动获取长度
后一个版本在f2py中正常工作:
f2py -c -m f2pychar f2pychar.f90
ipython
In [1]: import f2pychar
In [2]: print f2pychar.modul.chara
['h' 'e' 'l' 'l' 'o' 'W' 'o' 'r' 'l' 'd']
F2py应该理解它,但它似乎不理解。这是f2py中的一个严重错误。只需手动输入长度,如上面的后一个示例所示。没有区别,代码是优等的
到你的号码(2)。它不是数组(在Fortran中)。数组的规则在此不适用。但更重要的是,它是一个常数,你不能给它赋值,所以我真的不明白你的意思。如果您有一个字符变量,则可以毫无问题地分配较短的字符串:
character(10) :: ch = "abcd"
回答问题2:
fortran中的字符串在f2py中被视为字符数组。因此在您的例子中,mod.module.chara
是一个100
字符的数组(取决于fortran中指定的长度)。要将类似于'hello'
的内容输入句柄,可以执行以下操作:
for i,j in enumerate('hello'):
mod.modul.chara[i]=j
这将允许您传递字符串。对所有Fortran问题使用标记。您还使用python而不是python-3.5。python 3不是使用f2py3调用的吗?也许只有在我的Linux发行版上……假定长度字符常量在Fortran 90中是合法的。F2py应该理解它们。实际上,MCVE可以比您的示例短得多。三行就够了<代码>模块模块;字符(*),参数::chara=“helloWorld”;终端模块模块看不到阵列。我不明白你的要点(2)。@VladimirF:(1)感谢你的更正(2)我尝试使用f2py3和f2py3.5,但它并没有解决问题(3)如果我不能为字符指定一个可变长度,而我必须在编译时确定足够长的固定长度以包含任何合理的字符串,我就不会得到这个注释(4)。通过这种方式,如果字符串短于长度,则代码可以工作;如果字符串长,则由于内存不足而无法工作。正如您在第6段代码中看到的,Python要求字符串的长度与字符的长度相同。有没有办法插入短字符串?这很有效,谢谢。我想我会继续(2)的方法,除非有人提出一些建议来完成(1)
mod.modul.chara
是一个常数,这个命令应该会立即失败。@VladimirF这个方法对我有效,OP声称对他也有效。这可能是因为我们已经声明了字符串元素的长度,并且没有在fortran中为其赋值。如果它是参数
,它一定会崩溃。
for i,j in enumerate('hello'):
mod.modul.chara[i]=j