2011-04-26 27 views
37

Encontré estos símbolos en una declaración de función varias veces, pero no sé lo que significan.Significado de * & y ** & en C++

Ejemplo:

void raccogli_dati(double **& V, double **p, int N) { 
    int ultimo = 3; 
    V = new double * [N/2]; 
    for(int i=0; i < N/2; i++) { 
    V[i] = new double[N/2], std :: clog << "digita " << N/2 - i 
       << " valori per la parte superiore della matrice V: "; 
    for(int j=i; j < N/2; j++) 
     std :: cin >> V[i][j], p[ultimo++][0] = (V[i][j] /= sqrt(p[i][0]*p[j][0])); 
    } 
    for(int i=1; i < N/2; i++) 
    for(int j=0; j < i; j++) 
     V[i][j] = V[j][i]; 
} 
+0

En el código real o un libro? Para mí, solo parece una notación para una función general. Uno que devuelve un solo puntero, y el otro un puntero a un puntero. –

+0

Esas son referencias a punteros. –

+0

de esta manera: void raccogli_dati (double ** & V, double ** p, int N) { \t int ultimo = 3; \t V = nuevo doble * [N/2]; \t for (int i = 0; i > V [i] [j], \t \t p [ultimo ++] [0] = (V [i] [j]/= sqrt (p [i] [0] * p [j] [0])); } \t for (int i = 1; i sdffadsf

Respuesta

54

que está tomando el parámetro por referencia. Por lo tanto, en el primer caso está tomando un parámetro de puntero por referencia, de modo que cualquier modificación que haga al valor del puntero se reflejará fuera de la función. El segundo es similar al primero, con la única diferencia de que es un doble puntero. Vea este ejemplo:

void pass_by_value(int* p) 
{ 
    //Allocate memory for int and store the address in p 
    p = new int; 
} 

void pass_by_reference(int*& p) 
{ 
    p = new int; 
} 

int main() 
{ 
    int* p1 = NULL; 
    int* p2 = NULL; 

    pass_by_value(p1); //p1 will still be NULL after this call 
    pass_by_reference(p2); //p2 's value is changed to point to the newly allocate memory 

    return 0; 
} 
9

Eso está pasando un puntero por referencia en lugar de por valor. Esto, por ejemplo, permite alterar el puntero (no el objeto apuntado) en la función de tal manera que el código de llamada ve el cambio.

Compare:

void nochange(int* pointer) //passed by value 
{ 
    pointer++; // change will be discarded once function returns 
} 

void change(int*& pointer) //passed by reference 
{ 
    pointer++; // change will persist when function returns 
} 
+0

gracias por mencionar la diferencia en la persistencia –

10

En primer lugar es una referencia a un puntero, la segunda es una referencia a un puntero a un puntero. Consulte también las preguntas frecuentes en how pointers and references differ.

void foo(int*& x, int**& y) { 
    // modifying x or y here will modify a or b in main 
} 

int main() { 
    int val = 42; 
    int *a = &val; 
    int **b = &a; 

    foo(a, b); 
    return 0; 
} 
+1

Sé que realmente no debería, pero he votado positivamente esta respuesta simplemente porque contiene un a-puntero-a-puntero-a-una-referencia-a-una-alusión-a-la -significado de la vida. De alguna manera, creo que estamos a unos años de Deep Thought. – corlettk

5

int* es un puntero a un int. Entonces int*& debe ser una referencia a un puntero a int. Del mismo modo, int** es un puntero a un puntero a int, luego int ** & debe ser una referencia a un puntero a un puntero a un int.

+0

entiendo sus significados literales, ¿puede escribir un ejemplo para ilustrar de manera más efectiva entre ellos? – Sheldon

3

Para comprender esas frases echemos un vistazo a la par de cosas:

typedef double Foo; 
void fooFunc(Foo &_bar){ ... } 

Para que se supere una doble referencia.

typedef double* Foo; 
void fooFunc(Foo &_bar){ ... } 

ahora está pasando un puntero a un doble de referencia.

typedef double** Foo; 
void fooFunc(Foo &_bar){ ... } 

Por último, está pasando un puntero a un puntero a un doble por referencia. Si piensa en términos de typedefs como este, comprenderá el orden correcto de & y * más lo que significa.

3

*& significa que se recibe el puntero por referencia. Significa que es un alias para el parámetro que pasa. Por lo tanto, afecta el parámetro de paso.

#include <iostream> 
using namespace std; 

void foo(int *ptr) 
{ 
    ptr = new int(50); // Modifying the pointer to point to a different location 
    cout << "In foo:\t" << *ptr << "\n"; 
    delete ptr ; 
} 

void bar(int *& ptr) 
{ 
    ptr = new int(80); // Modifying the pointer to point to a different location 
    cout << "In bar:\t" << *ptr << "\n"; 
    // Deleting the pointer will result the actual passed parameter dangling 
} 
int main() 
{ 
    int temp = 100 ; 
    int *p = &temp ; 

    cout << "Before foo:\t" << *p << "\n"; 
    foo(p) ; 
    cout << "After foo:\t" << *p << "\n"; 

    cout << "Before bar:\t" << *p << "\n"; 
    bar(p) ; 
    cout << "After bar:\t" << *p << "\n"; 

    delete p; 

    return 0; 
} 

Salida:

Before foo: 100 
In foo: 50 
After foo: 100 
Before bar: 100 
In bar: 80 
After bar: 80