¿Por qué el asterisco está antes del nombre de la variable, en lugar de después del tipo?


¿Por qué la mayoría de los programadores de C nombran variables como esta:

int *myVariable;

En lugar de esto:

int* myVariable;

Ambos son válidos. Me parece que el asterisco es una parte del tipo, no una parte del nombre de la variable. ¿Alguien puede explicar esta lógica?

Author: Lundin, 2008-12-29

11 answers

Son EXACTAMENTE equivalentes. Sin embargo, en

int *myVariable, myVariable2;

Parece obvio que myVariable tiene type int*, mientras que myVariable2 tiene type int. En

int* myVariable, myVariable2;

Puede parecer obvio que ambos son de tipo int*, pero eso no es correcto ya que myVariable2 tiene tipo int.

Por lo tanto, el primer estilo de programación es más intuitivo.

 207
Author: luiscubal,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-11-30 18:28:44

Si lo miras de otra manera, *myVariable es del tipo int, lo que tiene algún sentido.

 99
Author: biozinc,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-29 19:25:26

Porque el * se une más estrechamente a la variable que al tipo:

int* varA, varB; // This is misleading

Sin embargo, incluso las mejores declaraciones de una sola línea me parecen contra-intuitivas, porque el * es parte del tipo. Me gusta hacer esto en su lugar:

int* varA;
int varB;

Como de costumbre, menos el compacto de su código, más legible es. ;)

 35
Author: ojrac,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-05-29 15:29:27

Algo que nadie ha mencionado aquí hasta ahora es que este asterisco es en realidad el " operador de dereferencia " en C.

*a = 10;

La línea anterior no significa que quiera asignar 10 a a, significa que quiero asignar 10 a cualquier ubicación de memoria a puntos. Y nunca he visto a nadie escribiendo

* a = 10;

Tiene usted? Así que el operador de desreferencia es casi siempre escrito sin espacio. Esto es probablemente para distinguirlo de un multiplicación rota a través de múltiples líneas:

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

Aquí *e sería engañoso, ¿no?

Bien, ahora qué significa realmente la siguiente línea:

int *a;

La mayoría de la gente diría:

Significa que a es un puntero a un valor int.

Esto es técnicamente correcto, a la mayoría de la gente le gusta verlo / leerlo de esa manera y esa es la forma en que los estándares modernos de C lo definirían (tenga en cuenta que el lenguaje C en sí es anterior a todos los ANSI y Normas ISO). Pero no es la única manera de verlo. También puede leer esta línea de la siguiente manera:

El valor desreferenciado de a es de tipo int.

Así que, de hecho, el asterisco en esta declaración también se puede ver como un operador de desreferencia, que también explica su ubicación. Y que a es un puntero no es realmente declarado en absoluto, está implícito por el hecho, que la única cosa que realmente puede desreferenciar es un puntero.

El estándar C solo define dos significados para el operador *:

  • operador indirecto
  • operador de multiplicación

Y indirection es solo un significado único, no hay un significado extra para declarar un puntero, solo existe indirection, que es lo que hace la operación dereference, realiza un acceso indirecto, por lo que también dentro de una declaración como int *a; este es un acceso indirecto (* acceso indirecto) y por lo tanto la segunda declaración anterior está mucho más cerca de la estándar que el primero.

 17
Author: Mecki,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-07-22 11:23:20

Voy a ir en una extremidad aquí y decir que hay una respuesta directa a esta pregunta, tanto para las declaraciones de variables como para los tipos de parámetro y retorno, que es que el asterisco debe ir junto al nombre: int *myVariable;. Para apreciar por qué, mira cómo declaras otros tipos de símbolo en C:

int my_function(int arg); para una función;

float my_array[3] para una matriz.

El patrón general, referido como declaración sigue uso , es que el tipo de un símbolo se divide en la parte antes del nombre, y las partes alrededor de el nombre, y estas partes alrededor del nombre imitan la sintaxis que usaría para obtener un valor del tipo a la izquierda:

int a_return_value = my_function(729);

float an_element = my_array[2];

Y: int copy_of_value = *myVariable;.

C++ lanza una extensión en las obras con referencias, porque la sintaxis en el punto donde se usan referencias es idéntica a la de los tipos de valor, por lo que podría argumentar que C++ adopta un enfoque diferente a C. Por otro lado, C++ conserva el mismo comportamiento de C en el caso de los punteros, por lo que las referencias realmente se destacan como el impar hacia fuera en este sentido.

 15
Author: Injektilo,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-10-14 15:30:55

Eso es solo una cuestión de preferencia.

Cuando se lee el código, distinguir entre variables y punteros es más fácil en el segundo caso, pero puede llevar a confusión cuando se ponen ambas variables y punteros de un tipo común en una sola línea (que a menudo se desaconseja por las directrices del proyecto, porque disminuye la legibilidad).

Prefiero declarar punteros con su signo correspondiente junto al nombre del tipo, por ejemplo,

int* pMyPointer;
 9
Author: macbirdie,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-07-31 15:34:55

Un gran guru dijo una vez: "Léelo a la manera del compilador, debes hacerlo."

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

Concedido esto estaba en el tema de la colocación de const, pero la misma regla se aplica aquí.

El compilador lo lee como:

int (*a);

No como:

(int*) a;

Si tiene el hábito de colocar la estrella junto a la variable, hará que sus declaraciones sean más fáciles de leer. También evita los problemas de la vista tales as:

int* a[10];
 6
Author: dgnuff,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-03-08 19:33:48

Porque tiene más sentido cuando tienes declaraciones como:

int *a, *b;
 2
Author: Greg Rogers,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-29 19:27:25

Para declarar múltiples punteros en una línea, prefiero int* a, * b; que declara más intuitivamente "a" como un puntero a un entero, y no mezcla estilos cuando declara igualmente "b". Como alguien dijo, no declararía dos tipos diferentes en la misma declaración de todos modos.

 2
Author: heyitsluke,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2012-10-18 05:25:34

En K&R, colocan el operador puntero junto al nombre de la variable en lugar del tipo. Personalmente, considero que ese libro es la máxima autoridad / biblia. También viniendo de un fondo de Objective-C, sigo la convención del nombre*.

 2
Author: Mahouk,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-03-08 08:16:35

Ya respondí a una pregunta similar en CP, y, como nadie mencionó eso, también aquí tengo que señalar que C es un lenguaje de formato libre, cualquier estilo que elija está bien mientras que el analizador puede hacer una distinción de cada token. Esta peculiaridad de C lleva a un tipo muy especial de concurso llamado Concurso de ofuscación C .

 1
Author: Frankie_C,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-08-01 18:18:51