我正在阅读高级Linux编程的第2章:
http://www.advancedlinuxprogramming.com/alp-folder/alp-ch02-writing-good-gnu-linux-software.pdf
在2.1.3 Using getopt_long
部分中,有一个示例程序有点像这样:
int main (int argc, char* argv[]) {
int next_option;
// ...
do {
next_option = getopt_long (argc, argv, short_options, long_options, NULL);
switch (next_option) {
case ‘h’: /* -h or --help */
// ...
}
// ...
引起我注意的是next_option被声明为int。函数getopt_long()显然返回一个int,表示短命令行参数,该参数在以下switch语句中使用。为什么可以将该整数与switch语句中的字符进行比较?
是否存在从char(单个字符?)到int的隐式转换?上面的代码如何有效? (参见链接pdf中的完整代码)
答案 0 :(得分:5)
C和C ++都没有一种类型可以将“字符”存储为带有一些专用字符特定属性的值。从这个意义上说,在C和C ++中都没有“字符”类型。
在C ++和C语言中,char
是整数类型。它包含数字。它只是一个最小的(在范围方面)整数类型。 char
和int
之间的转换存在,就像它存在于int
和long
或int
和short
之间一样。 char
在其他整数类型中没有特殊状态(char
类型与signed char
类型不同)。
C ++中'h'
形式的文字具有类型char
,但与任何其他整数类型相比,它与int
相当。这就是为什么你可以在case
标签中使用它在原始示例中使用的方式。
换句话说,您的原始代码与
一样“奇怪”switch (next_option) {
case 1L: ...
// ...
}
会。在这种情况下,switch
参数是int
,但案例标签是long
。代码有效。你觉得它令人惊讶吗?可能不是。您与'h'
的示例差别不大。
答案 1 :(得分:4)
你错了 - getopt_long(3)
返回一个int。
答案 2 :(得分:1)
有几个函数在C中返回int
,但在C ++中返回char
。当int
更有意义时返回char
只是一个古老的C文化决定。另外,在少数情况下,有必要让函数返回EOF
之类的标记。
答案 3 :(得分:0)
正如另一位回答者所说,你在这里提出错误的问题。但要回答你所做的问题问:
没有从char *到int的隐式转换。在x86机器上,int和char *都是32位长,因此显式转换是“安全的”:
int x = (int*) &someChar;
但非常不推荐!!!
在x64计算机上,这将无法正常工作! int保持32位长,但所有指针现在都是64位长...所以你将丢失数据!
答案 4 :(得分:0)
根据手册页,getopt_long返回int
。是的,有char
到int
的隐式演员表; char
只是一个字节的整数值。
因此,在这种情况下,在分配给next_option
时不会发生强制转换,但在case
语句中,您将字符常量与int
进行比较。当然,这是假设您将其编译为C ++。在C ++中,字符常量的类型为char
,但在C中它的类型为int
,因此如果将此代码编译为C,则根本没有类型转换。
(在你的问题中你提到char*
,但你可能意味着char
;这里没有使用指针。)
答案 5 :(得分:0)
将char视为8位int。您可以对字符执行整数运算,甚至可以将它们声明为无符号。如果你可以比较短期和长期,你不会感到惊讶。为什么比较char和int是不同的?