我发现这段代码出乎意料
module testmodule
integer, parameter :: LCHARS = 50
contains
subroutine init()
call foobar("foobar")
end subroutine
subroutine foobar(s)
character(len=*), intent(in) :: s
call bar(s)
end subroutine
subroutine bar(str)
character(len=LCHARS), intent(in) :: str
print *, str
end subroutine
end module
program foo
use testmodule
call init()
end program
Run Code Online (Sandbox Code Playgroud)
此代码打印依赖于编译器的垃圾.
我发现问题在于我正在跳过一个带有len=*字符串参数的例程,然后将其传递给字符串参数的指定长度的例程.
正是在幕后发生了什么,标准中描述的这种行为在哪里?我是否应该避免为字符例程参数指定长度,因为这种行为可能在任何时候发生而没有警告?
我这里有一个测试程序:
program test
implicit none
integer(4) :: indp
integer(4) :: t1(80)
indp = -3
t1(indp) = 1
write(*,*) t1(indp)
end program test
Run Code Online (Sandbox Code Playgroud)
第8行是错误的,因为indp是负数.但是当我编译它时使用'ifort'或'gfortran'它们都找不到这个错误.甚至使用valgrind来调试这个程序它也找不到这个错误.你有什么想法找到这种问题吗?
我正在使用gfortran的95+扩展.我有一个实用程序模块库,我想链接到其他项目,即作为库或共享对象/ DLL.但是,在Fortran中,我不明白如何在不保留模块接口的两个副本的情况下将接口与Fortran中的实现分开.
在C中,我将接口与实现分开,如:
api.h ?includes? impl.h
? ?
includes includes
? ?
user.c impl.c
Run Code Online (Sandbox Code Playgroud)
有没有办法在现代Fortran中实现相同的效果?我是否需要为用户提供.mod文件?
编辑:总结(我认为是)答案:
需要.mod文件,因为它们包含显式接口定义
模块没有标准的Fortran ABI - .mod文件将是特定于编译器的
实现隐藏问题的唯一直接分析方法是子模块,它在Fortran 2008中定义,并且gfortran不支持.
除了避免使用模块之外,@ High-Performance-Mark和Fedora页面提供的最实用的方法是分发仅用于接口的模块的包含文件以及用于实现的预编译.mods.
使用包含一些众所周知和烦人的旅行,包括潜在的重新定义公共块.
我有点惊讶,这里实际上没有一个简单的答案.
Fortran的新手(刚开始今天),自然对数出现问题:
PROGRAM log
IMPLICIT NONE
REAL :: x
PRINT *, "Enter a number:"
READ *, x
x = log (x)
PRINT *, "The natural log of x is:", x
END PROGRAM log
Run Code Online (Sandbox Code Playgroud)
编译器不断抛出错误:
x = log (x)
1
Error: Symbol at (1) is not appropriate for an expression
Run Code Online (Sandbox Code Playgroud)
其他内在函数工作正常.我究竟做错了什么?
嗯,这就是我今天的问题......
我正在编写一个模块过程,它有一个函数作为参数。这个模块看起来像这样:
module Integ
implicit none
<variables declaration>
contains
function Integral(a,b,f) result(res)
real, intent(in) ::a, b
real ::res
interface
pure function f(x)
real, intent(in) :: x
real :: f
endfunction
endinterface
<more code of function Integral>
endfunction Integral
endmodule Integ
Run Code Online (Sandbox Code Playgroud)
那么,到这里为止,一切都很好。当我尝试将此函数与Fortran 内在函数一起使用时,问题就会出现。即,在这段代码中:
program main
use Integ
implicit none
real ::res,a,b
a=3.0; b=4.0
res=Integral(a,b,sin) !<- This line does not work
!res=Integral(a,b,sen) !<- This line does work
contains
function sen(x)
real, intent(in) :: x
real :: sen
sen=sin(x)
endfunction
endprogram …Run Code Online (Sandbox Code Playgroud) 我想编写一些适用于不同类型的程序.我打算使用这里和这里描述的flibs中使用的"include"方法.我在这里给出一个简单的例子.
! -------------------------------------------------------------- !
module data_type
type ivalue
integer :: v
end type
type rvalue
real(8) :: v
end type
end module data_type
! -------------------------------------------------------------- !
module imod
use data_type, only: T => ivalue
include "template.f90"
end module imod
! -------------------------------------------------------------- !
module rmod
use data_type, only: T => rvalue
include "template.f90"
end module rmod
! -------------------------------------------------------------- !
module mod
use imod, only:
& ivalue => T,
& iprintme => printme
use rmod, only:
& rvalue …Run Code Online (Sandbox Code Playgroud) 我想在 fortran 90 中使用自动整数宽度描述符。我提到了输出格式:gfortran 中的太多空白
这个问题说我可以使用I0和F0,0用于“自动”宽度。这是我的示例代码(符合 GNU Fortran 编译器):
PROGRAM MAIN
IMPLICIT NONE
INTEGER :: i
REAL :: j
WRITE (*,*) 'Enter integer'
READ (*,100) i
100 FORMAT (I0)
WRITE (*,*) 'Enter real'
READ (*,110) j
110 FORMAT (F0.0)
WRITE (*,100) 'Integer = ',i
WRITE (*,110) 'Real = ',j
END PROGRAM
Run Code Online (Sandbox Code Playgroud)
存在运行时错误 (unit = 5, file = 'stdin')
Fortran runtime error: Positive width required in format
我误解了自动宽度描述符吗?我应该使用什么选项?
我只想知道returnFortran 2008中的语句是否过时,因为似乎没有必要在子例程和函数的末尾编写该语句。
它还有其他实用程序吗?
我决定尝试在Fortran 95中实现阶乘函数(f2py限制),但我的努力只产生两个返回类型不匹配错误.
解决方案的灵感
在Haskell中,我们可以做类似的事情
fac_helper n acc =
if n <= 1
then acc
else fac_helper (n - 1) (acc * n)
factorial n = fac_helper n 1
Run Code Online (Sandbox Code Playgroud)
试图解决方案:fac.f95
recursive function facHelper(n, acc) result(returner)
integer::n
integer::acc
integer::returner
if (n <= 1) then
returner = acc
else
returner = facHelper(n - 1, n * acc)
endif
end function facHelper
function factorial(n)
integer::n
integer::factorial
factorial = facHelper(n, 1)
end function factorial
Run Code Online (Sandbox Code Playgroud)
当fac.f95上使用GNU Fortran(GCC)4.8.3时
gfortran -std=f95 ./fac.f95 -o fac
结果是:
Error: Return type …Run Code Online (Sandbox Code Playgroud) 目前我正在使用 gfortran 6.1 在 mac 上编译 fortran95 源代码。我想知道是否可以使用相同的方法运行 FORTRAN 77 源代码。如果没有,有什么建议吗?