
pranfia
Si he declarado un puntero p
como int *p
; en el módulo principal, puedo cambiar la dirección contenida por p
asignando p = &a;
donde a
es otra variable entera ya declarada. Ahora quiero cambiar la dirección usando una función como:
void change_adrs(int*q)
{
int *newad;
q = newad;
}
Si llamo a esta función desde el módulo principal
int main()
{
int *p;
int a = 0;
p = &a; // this changes the address contained by pointer p
printf("The address is %u\n", p);
change_adrs(p);
printf("The address is %u\n", p); // but this doesn't change the address
return 0;
}
el contenido de la dirección no cambia. ¿Qué tiene de malo usar una función para la misma tarea?

matemático1975
En C, los argumentos de las funciones se pasan por valor. Por lo tanto, se hace una copia de su argumento y el cambio se realiza en esa copia, no en el objeto de puntero real que espera ver modificado. Deberá cambiar su función para aceptar un argumento de puntero a puntero y realizar el cambio en el argumento desreferenciado si desea hacer esto. Por ejemplo
void foo(int** p) {
*p = NULL; /* set pointer to null */
}
void foo2(int* p) {
p = NULL; /* makes copy of p and copy is set to null*/
}
int main() {
int* k;
foo2(k); /* k unchanged */
foo(&k); /* NOW k == NULL */
}
Si tiene el lujo de usar C++, una forma alternativa sería cambiar la función para aceptar una referencia a un puntero.
En C, las variables se pasan por valor: se pasa una copia del puntero a la función. Use otro puntero al puntero en su lugar:
void change(int **p, int *someOtherAddress)
{
*p = someOtherAddress;
}
int a = 1, b = 2;
int *p = &a;
printf("*p = %d\n", *p);
change(&p, &b);
printf("*p = %d\n", *p);
esto imprime
*p = 1
*p = 2

gruñido
Si desea modificar el contenido de una variable en una función en C, el puntero también es un tipo de variable, debe pasarlo por puntero o referencia indirecta usando siempre &
dirección y *
operadores de desreferencia. quiero decir *
El operador siempre se usa y va precedido al cambiar el valor de una variable.
#include <stdio.h>
#include <stdlib.h>
void changeIntVal(int *x) {
*x = 5;
}
void changePointerAddr(int **q) {
int *newad;
*q = newad;
}
void changePPAddr(int ***q) {
int **dummy;
*q = dummy;
}
int main() {
int *p;
int **pp;
int *tempForPP;
int a = 0;
printf("\n The address pointing by p -> %p, pp -> %p, value of a -> %d ", p, pp, a);
p = &a;
pp = &tempForPP;
printf("\n The address pointing by p -> %p, pp -> %p, value of a -> %d ", p, pp, a);
changeIntVal(&a); // ----
// |---
changePointerAddr(&p); // ---- |----> parts of what I mean
// |---
changePPAddr(&pp); // ----
printf("\n The address pointing by p -> %p, pp -> %p, value of a -> %d ", p, pp, a);
return 0;
}
Para un tipo de datos primitivo como un int
, los punteros dobles no son necesarios. Puede escribir directamente a la dirección donde se encuentra el int
se almacena, tratando su dirección como un puntero en la función que se llama. Esto es diferente a un char
matriz (“cadena”) donde el tamaño de lo que se apunta es variable y, por lo tanto, debe usar otro nivel de direccionamiento indirecto al cambiarlo desde dentro de una función llamada. Prueba esto:
void foo(int *oldVal)
{
int newVal = 99; // or whatever you want
*oldVal = newVal;
}
int main(int argc, char *argv[])
{
int someVal = 0;
foo(&someVal); // we send its address to foo()
printf("someVal is now %d.\n", someVal);
return EXIT_SUCCESS;
}

Omkant
Esto no cambiará el valor real de p
porque el q
en función es local a eso y el cambio en esa función no se reflejará en main
así que pasa la dirección de p
en lugar de pasar p
por valor
Use esta sintaxis a continuación
void change_adrs(int **q)
{
int * otheraddess;
*q = otheraddress;
}
y llamar asi change_adrs(&p);
O bien, tiene otra forma: cambie el tipo de devolución de la función y capture la dirección devuelta.
int* change_adrs(int *q)
{
int * otheraddess;
q = otheraddress;
return q;
}
int main()
{
p = change_adrs(p);
return 0;
}
Está pasando el puntero por valor. Si necesita cambiar el puntero dentro de la función, páselo por referencia… doble puntero.
– Alok Guardar
17 de noviembre de 2012 a las 13:43