Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/fortran/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C_INT fortran类型需要什么?C和Fortran整数有这么大的不同吗?_Fortran_Fortran Iso C Binding - Fatal编程技术网

C_INT fortran类型需要什么?C和Fortran整数有这么大的不同吗?

C_INT fortran类型需要什么?C和Fortran整数有这么大的不同吗?,fortran,fortran-iso-c-binding,Fortran,Fortran Iso C Binding,如果我在fortran中将一个整数声明为: INTEGER(C_INT)::i那么,如果我理解正确,将其传递给C函数是安全的。现在不考虑总是以这种方式声明整数的额外麻烦,有没有理由不总是将变量声明为C-可互操作的?这样做有什么坏处吗 同样,对于简单的整数,C_INT与传统的Fortran整数有什么不同?Fortran和C整数实际上是不同的吗?C整数的大小通常是固定的,因为操作系统是使用C编译的,系统绑定是作为C头发布的。操作系统设计者选择一种常见的模型,如(用于64位指针操作系统),然后C编译器

如果我在fortran中将一个整数声明为:
INTEGER(C_INT)::i
那么,如果我理解正确,将其传递给C函数是安全的。现在不考虑总是以这种方式声明整数的额外麻烦,有没有理由不总是将变量声明为C-可互操作的?这样做有什么坏处吗


同样,对于简单的整数,
C_INT
与传统的Fortran整数有什么不同?Fortran和C整数实际上是不同的吗?

C整数的大小通常是固定的,因为操作系统是使用C编译的,系统绑定是作为C头发布的。操作系统设计者选择一种常见的模型,如(用于64位指针操作系统),然后C编译器遵循此选择

但是Fortran编译器更免费。您可以将它们设置为不同的配置。Fortran编译器设置为使用8字节的默认整数和8字节的默认实数仍然是完全符合标准的!(C也可以,但选择在操作系统中是固定的。)

因为C和Fortran中的整数不必匹配,所以您需要一种机制来可移植地选择C可互操作类型,无论默认类型是什么

这不仅仅是学术性的。您可以找到像MKL这样的库,它们是用8字节整数编译的(ILP64模型,C的通用操作系统不使用它)


因此,当您调用一些API,一些接口在C中定义的函数时,您希望正确地调用它,而不依赖于Fortran编译器的设置。这就是C-可互操作类型的用例。如果一个C函数需要一个
int
,你给它一个
整数(C_int)
,你不在乎Fortran默认整数是否相同。

基本上没有根本的缺点,在同一个编译器上也没有根本的好处

即使在icc中,长整数在32位和64位操作系统上也是不同的,因此您需要知道(或定义您在c端想要什么)

唯一一个明显是4字节的是C_INT32_T,因此我通常使用它。使用C_INT32_T,将其定义为您希望的固定位数,这更像是一种“未来证明”

这些都在iFort上给出了一个4字节的整数

USE ISO_C_BINDING, ONLY : C_INT, C_INT32_T
Integer                 :: 
INTEGER(KIND=4)         ::   !"B"  At least on iFort
INTEGER*4                    !"A"  
INTEGER(KIND=C_INT)     ::
INTEGER(KIND=C_INT32_T) ::   !"C"
通常人们会发现使用“A”样式的旧代码

我经常使用“B”的风格,但即使这是一个“事实标准”,它也不符合“标准”

然后,当我开始关注可移植性时,我运行并将“B”样式更改为“C”样式,然后考虑到以后可能会使用gfortran编译器编译的其他人,我就不会那么心痛了。。。甚至是其他编译器

单字节:

BYTE                        :: !Good
INTEGER(KIND=1)             ::
INTEGER(KIND=C_SIGNED_CHAR) ::
INTEGER(KIND=C_INT8_T)      :: !Best
两个字节:

INTEGER(KIND=2)            ::
INTEGER(KIND=C_INT16_T)    :: !Best
INTEGER(KIND=C_SHORT)      ::
8字节:

INTEGER(KIND=8)            ::
INTEGER(KIND=C_INT64_T)    :: !Best
INTEGER(KIND=C_LONG_LONG)  ::
虽然这看起来有点可疑。。。我们也可以说:

LOGICAL(KIND=4)         ::
LOGICAL(KIND=C_INT32_T) :: !Best here may be C_bool and using 1-byte logical in fortran...? Assuming that there is no benefit with the size of the logical being the same as some float vector
LOGICAL(KIND=C_FLOAT)   ::

在您和我使用的编译器中可能是相同的,但是有些编译器的c_int与c_long匹配,但是为什么Fortran和c之间的默认int大小会不同呢?我可以,也许是愚蠢的,用一个默认int大小的c编译器编译我的c代码,然后,用我的fortran编译器,将默认int大小设置为另一个大小。我无法想象
C_INT
会将这些隔离开来。你根本不在乎存储空间大小,这正是我想说的。您通常希望与某些API兼容。