_Complex long int [英] _Complex long int
问题描述
tl;博士;
问_Complex long int
中的int
是什么意思?为什么它合法?
Q what does int
mean in _Complex long int
? Why is it legal?
我正在移植一些 32 位代码以保证 64 位安全.在一个地方,我注意到它使用:
I was porting some 32-bit code to be 64-bit safe. In one place I noted it uses:
static __complex__ long int i32X[256];
一个愚蠢的搜索和替换为 int32_t 更改long int"给了我一个编译错误.__complex__ 是一种较旧的 GNUism,已被标准 _Complex 取代.这是重现问题的简短代码片段:
A dumb search and replace changing "long int" for int32_t gave me a compilation error. __complex__ is an older GNUism which has been replaced by the standard _Complex. Here is a short code snippet to reproduce the issue:
#include <complex.h>
#include <inttypes.h>
typedef _Complex long int WhyAmILegal;
typedef _Complex int32_t Snafu;
typedef int32_t _Complex Snafu2;
在gcc下编译给出:
complextest.c:6:26: error: expected ‘=’, ‘,’, ‘;’, ‘asm’ or ‘__attribute__’ before ‘Snafu’
typedef _Complex int32_t Snafu;
^~~~~
complextest.c:8:17: error: two or more data types in declaration specifiers
typedef int32_t _Complex Snafu2;
(草案)C11 标准 说:
"共有三种复杂类型,指定为float _Complex、double_Complex, and long double _Complex.43) (复杂类型是有条件的实现不需要支持的功能;见 6.10.8.3.)真正的浮动类型和复杂类型统称为浮动类型."
"There are three complex types, designated as float _Complex, double _Complex, and long double _Complex.43) (Complex types are a conditional feature that implementations need not support; see 6.10.8.3.) The real floating and complex types are collectively called the floating types."
所以这里的错误似乎是当只有浮点复杂类型是合法的时,我试图请求一个整数复杂类型._Complex long
的意思其实更像是_Complex long double
.我认为这可能是 gcc 解析器中的一个错误,但是
So the bug here would seem to be that I am trying to request an integral complex type when only floating point complex types are legal.
The meaning of _Complex long
is actually more like _Complex long double
.
I thought it might be a bug in gcc's parser, however
_Complex long int
在 clang online 下也能很好地编译.
compiles just fine under clang online as well.
那么为什么 int 在这里是合法的".
So why is int 'legal' here.
感谢@Keith-Thompson 指出整数复数是一种 GNU 扩展并且受 clang 支持.
Thanks to @Keith-Thompson's for pointing out that integral complex numbers are a GNU extension and one that is supported by clang.
另一个数据点.以下程序:
Another data point. The following program:
#include <complex.h>
#include <inttypes.h>
#include <stdio.h>
typedef _Complex long int ComplexLong;
typedef _Complex short int ComplexShort;
typedef _Complex int ComplexInt;
int main(void)
{
fprintf(stderr,"sizeof(_Complex long int)=%d
",sizeof(ComplexLong));
fprintf(stderr,"sizeof(_Complex int)=%d
",sizeof(ComplexInt));
fprintf(stderr,"sizeof(_Complex short int)=%d
",sizeof(ComplexShort));
fprintf(stderr,"sizeof(short int)=%d
",sizeof(short int));
fprintf(stderr,"sizeof(int)=%d
",sizeof(int));
fprintf(stderr,"sizeof(long int)=%d
",sizeof(long int));
return 0;
}
编译使用:
all: complextest complextest32
complextest: complextest.c
$(CC) -o$@ $<
complextest32: complextest.c
$(CC) -m32 -o$@ $<
when(使用gcc编译)并运行给出:
when (compiled using gcc) and run gives:
>./complextest
sizeof(_Complex long int)=16
sizeof(_Complex int)=8
sizeof(_Complex short int)=4
sizeof(short int)=2
sizeof(int)=4
sizeof(long int)=8
>./complextest32
sizeof(_Complex long int)=8
sizeof(_Complex int)=8
sizeof(_Complex short int)=4
sizeof(short int)=2
sizeof(int)=4
sizeof(long int)=4
所以 _Complex long int
像 long
不能以架构不变的方式指定.您应该使用 _Complex int
或 _Complex short
以稍微提高可移植性.
So _Complex long int
like long
cannot be specified in an architecture invariant manner. You should use _Complex int
or _Complex short
to be slightly more portable.
推荐答案
这是一个 gcc 扩展,你可以通过在(或多或少)符合 C 模式下编译看到:
It's a gcc extension, as you can see by compiling in (more or less) conforming C mode:
$ cat c.c
_Complex double cd;
_Complex long int cli;
$ gcc -c c.c
$ gcc -c -std=c11 -pedantic c.c
c.c:2:1: warning: ISO C does not support complex integer types [-Wpedantic]
_Complex long int cli;
^~~~~~~~
$
这是记录在 gcc 手册中:
ISO C99 支持复杂的浮点数据类型,并作为 GCC 的扩展在 C90 模式和 C++ 中支持它们.GCC 还支持复杂的不属于 ISO C99 的整数数据类型.
ISO C99 supports complex floating data types, and as an extension GCC supports them in C90 mode and in C++. GCC also supports complex integer data types which are not part of ISO C99.
毫无疑问,clang 支持相同的扩展.
clang, not surprisingly, supports the same extension.
要回答添加的问题,_Complex
是一个类型说明符._Complex int32_t
无效,原因与 unsigned int32_t
无效.类型说明符不能应用于 typedef.
To answer the added question, _Complex
is a type specifier. _Complex int32_t
is invalid for the same reason unsigned int32_t
is invalid. Type specifiers can't be applied to typedefs.
这篇关于_Complex long int的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!