注意:这个问题是关于星号(*
)的位置。
在我看到的大多数C代码中(例如,在Beej's guide to network programming中),所有变量声明/定义都使用T *name
格式,即将*
绑定到变量名称。指针被认为属于变量,而不是类型。
在我看到的大多数C ++代码中,格式为T* name
,即它将*
绑定到变量的类型。指针被认为属于类型,而不是变量。我自己,作为纯C ++编码器,也使用这种格式,因为指向类型的指针明显(对我来说)属于类型,而不是变量。 (很明显,即使是C ++标准也在示例中使用了这种格式。:))
是否有(历史性)原因?当程序员开始做C ++时,思维方式是否有所改变?
如果一个C编码器(使用前一种格式)可以解释他/她使用它的原因,而不是后者,也会很好。
答案 0 :(得分:23)
如果我冒险猜测,我会说这是因为C ++人员更有可能认为类型信息本身就是一种东西,因为模板可以在编译时以编程方式操作类型。他们也不太可能在同一声明中声明几个变量。
T*
样式将类型信息集中在一个地方并使其脱颖而出,如果您从未声明,使用此语法的T* foo, bar;
之类的内容引起的混淆不是问题同一陈述中的两个变量。
就个人而言,我发现T*
风格非常令人讨厌并且非常不喜欢它。 *
是类型信息的一部分,这是真的,但编译器解析它的方式使它实际上附加到名称而不是类型。我认为T*
方式掩盖了正在发生的重要事情。
在我的观察中,似乎我在C ++社区中很少见。我注意到你对最流行的风格也有同样的看法。
当然,要清楚,任何一种风格都适用于任何一种语言。但我确实注意到你做了同样的事情,一种风格在C代码中往往更常见,另一种在C ++中更常见。
答案 1 :(得分:16)
来自Stroustrup's C++ Style and Technique FAQ。
“典型的C程序员”写
int *p;
并解释它“*p
是什么是int
”强调语法,并且可能指向C(和C ++)声明语法争论风格的正确性。实际上,*
绑定到语法中的p
名称。“典型的C ++程序员”编写
int* p;
并解释它“p
是指向int
”强调类型的指针。实际上p
的类型是int*
。我显然更喜欢这种强调,并认为它对于使用C ++的更高级部分非常重要。
答案 2 :(得分:14)
就个人而言,我不同意这一点 - 我不认为有这样做的C或C ++方式。我从未见过任何证据表明这一点。但是,我确实假设为什么带有星号的语法更靠近C中声明的变量名。
在C中(至少在C89中,绝大多数C在使用中),您必须在块的顶部声明所有变量。这导致程序员在做
T a, b, c;
相对而言,在C ++中这种情况很少见。 (在C ++中,您声明变量接近于它们的使用位置,变量通常具有构造函数参数等;因此很少在一行上声明多个对象)
这也恰好是语法重要的唯一情况,因为声明
T* a, b, c;
声明一个指针,而不是程序员可能期望的三个指针。
由于在一行中放置多个声明在C中更常见,并且也是唯一一个星号位置很重要的情况,程序员更有可能将星号与变量相关联。
那就是说,我从未见过任何证据 - 这只是猜想。
答案 3 :(得分:12)
有几个人提到非常好的观点。我只想指出,虽然C非常强烈地保留了“声明反映使用”的含义,但C ++却没有。 C ++中的几个声明符不反映声明中的用法;
int &ref; // but "&ref" has type "int*", not "int".
int &&ref; // but "&&ref" is not valid at all.
我认为编写不同的C ++程序员实际上并不认为这是他们的理由,但这可能会阻止C ++书籍作者提及它,这可能会影响那些C ++程序员。
答案 4 :(得分:9)
C程序员倾向于使用一种风格而C ++程序员使用其他风格的原因很简单:Kernighan& Ritchie在their book中使用了“C风格”,而Stroustrup在his book中使用了“C ++风格”。
答案 5 :(得分:6)
在K& R中,他们使用type *name
符号,因此可能是许多C程序员得到它的地方。
答案 6 :(得分:5)
因为Bjarne有后见之明的好处:他意识到C声明符语法是“失败的实验”(读:C声明符语法被延迟)。其他人已经得到了其他人的回答。
答案 7 :(得分:2)
答案 8 :(得分:2)
只是引起争议:
int* a; int* b;
int *a;
int* a, * b, * c;
int* (* func)()
。还有其他C元素被错误使用,例如const
,它也属于右侧! int const a;
。这通常放在类型的左侧,尽管属于左侧的类型。必须修改许多编译器来处理这种用法。在C ++中,您可以观察到这与常量方法一致,因为编译器无法推断它是否放在左侧:int A::a() const
。对于const
,restricted
以及int const *
等声明的朋友的嵌套使用,这也会中断。 const
的常规用法表明这是一个指向整数的常量指针,但实际上是int *const
。
你一直都做错了,把一切都放在右边。
答案 9 :(得分:1)
C声明遵循与表达式相同的规则(例如优先级)。事实上,考虑像
这样的声明是完全有效的int *foo;
将表达式*foo
的类型(即应用于foo
的间接运算符)声明为int
而不是foo
作为int*
类型
然而 - 正如其他人已经指出的那样 - 在C ++中,将类型视为单独的,并且 - 由于模板 - 可修改的实体,因此使用像
这样的声明是有意义的。int* foo;