Answers:
auto
是类似的修饰符static
。它定义了变量的存储类。但是,由于局部变量的默认值为auto
,因此通常不需要手动指定它。
此页面列出了C中的不同存储类别。
auto
。tigcc.ticalc.org/doc/keywords.html#auto
_Thread_local
更多详细信息:en.cppreference.com/w/c/language/storage_duration和stackoverflow.com/a/14289720/6557621
如果您阅读了IAQ(不常见问题)列表,您会知道auto主要用于定义或声明车辆:
auto my_car;
始终停在户外的车辆:
extern auto my_car;
对于那些缺乏幽默感并且想要“只是事实的女士”的人:简短的回答是,根本没有任何理由要使用auto
。唯一允许您使用auto
的变量是已经具有auto
存储类的变量,因此您只是指定了无论如何都会发生的事情。尝试auto
在没有auto
存储类的将导致编译器拒绝您的代码。我想如果您想获得技术知识,则您的实现不必是编译器(而是编译器),并且从理论上讲,它可以在发出诊断后继续编译代码(但事实并非如此)。
kaz的小附录:
还有:
static auto my_car;
这需要根据ISO C进行诊断。这是正确的,因为它声明汽车已损坏。诊断是免费的,但是关闭仪表板灯将花费您80美元。(如果您从eBay购买了用于板载诊断的USB加密狗,则不超过20个)。
前面提到的extern auto my_car
还需要进行诊断,因此,除负责停车执法的市政人员外,它永远不会通过编译器运行。
如果您extern static auto ...
在任何代码库中都看到很多内容,则说明您处于困境中。在整个地方变成Rust之前,立即寻找更好的工作。
char auto my_car;
该auto
关键字是在C语言中无用。之所以这样,是因为在C语言之前,存在一种B语言,其中使用该关键字来声明局部变量是必需的。(B被开发为NB,后来成为C)。
如您所见,手册中包含大量示例auto
。之所以如此,是因为没有int
关键字。需要使用某种关键字来说“这是变量的声明”,并且该关键字还指示它是局部变量还是外部变量(auto
与extrn
)。如果您不使用任何一个,则将出现语法错误。也就是说,x, y;
它本身不是声明,而是声明auto x, y;
。
由于在开发语言时必须将用B编写的代码库移植到NB和C上,因此该语言的较新版本带来了一定的负担,从而提高了向后兼容性,从而减少了工作量。在的情况下auto
,程序员不必搜寻每次出现的情况auto
并将其删除。
从手册中可以明显看出,C中现在过时的“隐式int”残骸(能够在前面main() { ... }
不写任何东西int
)也来自B。这是支持B代码的另一种向后兼容性功能。函数没有在B中指定的返回类型,因为没有类型。一切都是一个字,就像许多汇编语言一样。
注意如何声明一个函数extrn putchar
,然后唯一使它成为标识符使用的函数:它用于函数调用表达式中,如putchar(x)
,这就是告诉编译器将该无类型字视为函数指针的原因。
C语言auto
中的关键字指示变量在块本地。由于这是块作用域变量的默认值,因此它是不必要且很少使用的(我认为我从未见过在讨论该关键字的文本示例中使用它)。如果有人可以指出auto
需要使用以获得正确的解析或行为的情况,我会很感兴趣。
但是,在C ++ 11标准中,auto
关键字已被“劫持”以支持类型推断,其中变量的类型可以从其初始值设定项的类型中获取:
auto someVariable = 1.5; // someVariable will have type double
添加类型推断主要是为了支持在模板中声明变量或从模板函数中返回,在这些函数中,基于模板参数的类型(或在实例化模板时由编译器推导的类型)通常很难手动声明。
auto
与存储类无关,它与可见性无关。
auto
关键字类似于在Python中包含分号,以前的语言(B
)要求使用该关键字,但是开发人员意识到它是多余的,因为大多数情况是auto
。
我怀疑它留给了从B到C的过渡。简而言之,一种用途是与B语言兼容。
例如在B和80年代C:
/* The following function will print a non-negative number, n, to
the base b, where 2<=b<=10. This routine uses the fact that
in the ASCII character set, the digits 0 to 9 have sequential
code values. */
printn(n, b) {
extrn putchar;
auto a;
if (a = n / b) /* assignment, not test for equality */
printn(a, b); /* recursive */
putchar(n % b + '0');
}
Auto关键字是一个存储类(决定变量和存储位置生存期的某种技术)。它具有这样一种行为,即该关键字的Help所创建的变量的寿命(lifetime)仅驻留在花括号内
{
auto int x=8;
printf("%d",x); // here x is 8
{
auto int x=3;
printf("%d",x); // here x is 3
}
printf("%d",x); // here x is 8
}
auto
只能用于块作用域变量。extern auto int
之所以是垃圾,是因为编译器无法确定它是使用外部定义还是使用自动定义覆盖extern(auto和extern的存储持续时间完全不同,例如static auto int
,这显然也是垃圾)。它总是可以选择以一种方式解释它,而是选择将其视为错误。
auto
确实提供了一个功能,并且启用了功能内的“一切都是整数”规则。与函数外部不同,在函数内部将错误a=3
解释为定义,int a =3
因为赋值在文件作用域中不存在,这a=3
是函数内部的错误,因为显然编译器始终将其解释为对外部变量的赋值,而不是对定义的赋值(即使存在没有extern int a
在功能上还是在文件范围内向前声明),但像符static
,const
,volatile
或auto
将意味着这是一个定义和编译器把它作为一个定义,但auto
没有其他说明符的副作用。auto a=3
因此是隐式的auto int a = 3
。诚然,signed a = 3
具有相同的效果,unsigned a = 3
并且始终是unsigned int。
还要注意“ auto
对是否将对象分配给寄存器没有影响(除非某些特定的编译器对此有所注意,但这似乎不太可能)”
我确定您熟悉C中的存储类说明符,即“ extern”,“ static”,“ register”和“ auto”。其他答案中几乎给出了“ auto”的定义,但是我不确定“ auto”关键字的可能用法,但我认为它取决于编译器。您会看到,关于存储类说明符,有一条规则。我们不能为变量使用多个存储类说明符。这就是为什么静态全局变量不能被外部化的原因。因此,它们仅对文件已知。进入编译器设置时,可以启用速度优化标记。编译器优化的方法之一是 它查找没有存储类说明符的变量,然后根据高速缓存的可用性和其他一些因素进行评估,以查看是否应使用寄存器说明符来处理该变量。现在,如果我们想优化代码以提高速度,同时又知道程序中的特定变量不是很重要,那么我们甚至不希望编译器将其视为寄存器。我虽然输入了auto,但是由于键入“ register auto int a;”,编译器将无法向变量添加寄存器说明符。或“自动注册int a”;引发使用多个存储类说明符的错误。综上所述,我认为auto可以禁止编译器通过优化将变量视为寄存器。如果我们想优化代码以提高速度,同时又知道程序中的特定变量不是很重要,又不想编译器甚至将其视为寄存器,该怎么办?我虽然输入了auto,但是由于键入“ register auto int a;”,编译器将无法向变量添加寄存器说明符。或“自动注册int a”;引发使用多个存储类说明符的错误。综上所述,我认为auto可以禁止编译器通过优化将变量视为寄存器。如果我们想优化代码以提高速度,同时又知道程序中的特定变量不是很重要,又不想编译器甚至将其视为寄存器,该怎么办?我虽然输入了auto,但是由于键入“ register auto int a;”,编译器将无法向变量添加寄存器说明符。或“自动注册int a”;引发使用多个存储类说明符的错误。综上所述,我认为auto可以禁止编译器通过优化将变量视为寄存器。引发使用多个存储类说明符的错误。综上所述,我认为auto可以禁止编译器通过优化将变量视为寄存器。引发使用多个存储类说明符的错误。综上所述,我认为auto可以禁止编译器通过优化将变量视为寄存器。
该理论不适用于GCC编译器,但是我没有尝试过其他编译器。
auto
可以指定但默认情况下不会发生的情况?