当前位置:  开发笔记 > IOS > 正文

为什么变量名之前的星号,而不是类型之后?

如何解决《为什么变量名之前的星号,而不是类型之后?》经验,为你挑选了8个好方法。

为什么大多数C程序员都将变量命名为:

int *myVariable;

而不是像这样:

int* myVariable;

两者都有效.在我看来,星号是类型的一部分,而不是变量名称的一部分.谁能解释这个逻辑?



1> luiscubal..:

它们完全等同.但是,在

int *myVariable, myVariable2;

很明显,myVariable的类型为int*,而myVariable2的类型为int.在

int* myVariable, myVariable2;

似乎很明显两者都是int*类型,但是因为intmyVariable2类型不正确.

因此,第一种编程风格更直观.


也许,但我不会在一个声明中混合和匹配类型.
@Kupiakos只有在你根据"声明跟随使用"学习C的声明语法之后才会更有意义.声明使用与使用相同类型变量完全相同的语法.声明一个int数组时,它看起来不像:`int [10] x`.这根本不是C的语法.语法显式解析为:`int(*x)`,而不是`(int*)x`,因此在左边放置星号只是误导并且基于对C声明语法的误解.
@BobbyShaftoe同意.即使在阅读了这里的每一个论点之后,我仍然坚持使用`int*someVar`进行个人项目.这更有意义.
更正:因此,您不应该在一行上声明多个变量.一般来说,你不应该根据其他一些不相关的,坏的和危险的编码风格来激发某种编码风格.
这就是为什么我坚持每个指针声明一个变量。如果您执行`int * myVariable,则绝对不会造成混淆。int myVariable2;`代替。

2> biozinc..:

如果你以另一种方式看待它,那*myVariable就是类型int,这是有道理的.


在这种情况下,这一点可能会产生误导:`int x = 5; int*pointer =&x;`,因为它建议我们将int`*pointer`设置为某个值,而不是`pointer`本身.
它有点整洁,因为你可以想象没有任何实际的指针类型.只有在适当引用或取消引用时,才会为您提供一种原始类型.
这是我最喜欢的解释,效果很好,因为它解释了C的一般声明怪癖 - 甚至是恶心和粗糙的函数指针语法.
qonf:NULL不是一个类型.`myVariable`可以为NULL,在这种情况下`*myVariable`会导致分段错误,但没有类型NULL.

3> ojrac..:

因为*更接近变量而不是类型:

int* varA, varB; // This is misleading

然而,即使是最好的单行声明对我来说也是违反直觉的,因为*是该类型的一部分.我喜欢这样做:

int* varA;
int varB;

像往常一样,代码越紧凑,可读性越强.;)



4> Mecki..:

到目前为止,没有人在这里提到的是这个星号实际上是C中的" 取消引用运算符 ".

*a = 10;

该线之上并不意味着我要分配10a,这意味着我要分配10到任何内存位置a点.我从未见过有人在写作

* a = 10;

你呢?因此,取消引用运算符几乎总是在没有空格的情况下编写.这可能是为了将它与跨越多行的乘法区分开来:

x = a * b * c * d
  * e * f * g;

*e会误导,不是吗?

好的,现在以下行实际意味着什么:

int *a;

大多数人会说:

这意味着它a是一个指向int值的指针.

这在技术上是正确的,大多数人喜欢以这种方式查看/阅读它,这就是现代C标准定义它的方式(注意语言C本身早于所有ANSI和ISO标准).但这不是看待它的唯一方式.您还可以按如下方式阅读此行:

取消引用的值a是类型int.

所以事实上,这个声明中的星号也可以看作是一个解引用运算符,它也解释了它的位置.这a是一个指针根本没有真正声明,它隐含的事实是,你唯一可以解除引用的是指针.

C标准仅为*运营商定义了两个含义:

间接运算符

乘法运算符

间接只是一个单一的含义,没有额外的意义来声明指针,只有间接,这是取消引用操作所做的,它执行间接访问,因此在这样的语句中int *a;也是间接访问(*均值)间接访问)因此上面的第二个陈述比第一个陈述更接近标准.


谢谢你让我免于在这里写下另一个答案.顺便说一下,我通常读取`int a,*b,(*c)();`就像"将以下对象声明为`int`:对象`a`,`b`指向的对象,以及从`c`"指向的函数返回的对象.

5> Injektilo..:

我将在这里说明这个问题的答案是直接的,无论是变量声明还是参数和返回类型,都应该是星号旁边的名字:int *myVariable;.要了解原因,请查看如何在C中声明其他类型的符号:

int my_function(int arg); 一个功能;

float my_array[3] 对于一个数组.

一般模式,称为声明跟随使用,是符号的类型被分割成名称前面的部分,以及名称周围的部分,名称周围的这些部分模仿您将用于获取的名称左侧类型的值:

int a_return_value = my_function(729);

float an_element = my_array[2];

并且:int copy_of_value = *myVariable;.

C++在引用中抛出了一个扳手,因为在使用引用时的语法与值类型的语法相同,所以你可以说C++对C采用不同的方法.另一方面,C++保留相同的在指针的情况下C的行为,所以在这方面引用确实是奇怪的.



6> macbirdie..:

这只是一个偏好问题.

当您阅读代码时,在第二种情况下区分变量和指针会更容易,但是当您将一个常见类型的变量和指针放在一行中时可能会导致混淆(本身通常不鼓励项目指南,因为降低了可读性).

我更喜欢用类型名称旁边的相应符号声明指针,例如

int* pMyPointer;


问题是关于C,没有参考.

7> The_Androcto..:

在K&R中,它们将指针运算符放在变量名称旁边而不是类型.就个人而言,我认为这本书是最终的C权威/圣经.同样来自Objective-C背景,我遵循*name约定.



8> dgnuff..:

一位伟大的大师曾经说过"你必须按照编译器的方式阅读它."

http://www.drdobbs.com/conversationsa-midsummer-nights-madness/184403835

当然这是关于const放置的主题,但同样的规则适用于此.

编译器将其读取为:

int (*a);

不是:

(int*) a;

如果您养成将星形放在变量旁边的习惯,它将使您的声明更容易阅读.它还避免了眼睛,如:

int* a[10];

推荐阅读
mylvfamily
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有