Confusion con tipos de referencia

18/12/2008 - 15:58 por Carlos | Informe spam
Hola tengo una confusion con los tipos por referencia. Se dice que una
variable que guarda un tipo por referencia solo guarda un puntero o
direccion y no realmente el valor.

Pero en este ejemplo yo pensaba que con mandar la variable como parametro
era suficiente y no habia por tanto que ponerle "ref":

private void A()
{
DataTable dt = new DataTable();
B(dt);
//aqui dt NO es null.
}
private void B(DataTable dt)
{ ...
dt = null;
}

Para que realmente dt se vuelva null en el metodo B() tengo que mandarla
por referencia:

private void A()
{
DataTable dt = new DataTable();
B(ref dt);
//aqui dt SI es null.
}
private void B(ref DataTable dt)
{ ...
dt = null;
}

Es asi o estoy confundido? hay que mandar entonces un puntero a un puntero?

gracias
 

Leer las respuestas

#1 Alberto Poblacion
18/12/2008 - 19:49 | Informe spam
"Carlos" <carl> wrote in message
news:%
Hola tengo una confusion con los tipos por referencia. Se dice que una
variable que guarda un tipo por referencia solo guarda un puntero o
direccion y no realmente el valor.

Pero en este ejemplo yo pensaba que con mandar la variable como parametro
era suficiente y no habia por tanto que ponerle "ref":

private void A()
{
DataTable dt = new DataTable();
B(dt);
//aqui dt NO es null.
}
private void B(DataTable dt)
{ ...
dt = null;
}



Correcto. En la llamada a B estás pasando dt por valor. Como dt es un
tipo-referencia, estás pasando el valor de la referencia. A través de dicho
valor puedes cambiar los contenidos a los que se refiere la referencia, pero
no la propia referencia, ya que sólo tienes una _copia_ del valor de ésta.
Lo que sí podrías hacer dentro del método B es dt.Tables.Add(...) y se
añadiría una tabla en el dt que tienes dentro de A (cosa que no ocurriría si
dt fuera un tipo-valor en lugar de un tipo-referencia).

Para que realmente dt se vuelva null en el metodo B() tengo que mandarla
por referencia:



Exacto. Aquí, en lugar del valor de la referencia, estás pasando la
referencia de la referencia, y por lo tanto B puede modificar no sólo los
contenidos a los que se refiere la referencia, sino también la propia
referencia (cosa que no ocurría cuando pasabas el valor de la referencia).


private void A()
{
DataTable dt = new DataTable();
B(ref dt);
//aqui dt SI es null.
}
private void B(ref DataTable dt)
{ ...
dt = null;
}


Es asi o estoy confundido? hay que mandar entonces un puntero a un
puntero?



Si quieres cambiar el propio puntero (es decir, "hacerlo a apuntar a
otro sitio", y no solamente "cambiar el contenido de la zona de memoria a la
que apunta el puntero"), entonces hay que pasar un puntero al puntero. Esto
no es nuevo de C#, ya ocurría en el C tradicional cuando manejabas
explícitamente punteros en lugar de manejar referencias.

Preguntas similares