Hoy revisando algunos libros de Java, me encontré con algunos en donde sorprendentemente dicen una GRAN mentira. De hecho, muchos sitios en internet manejan que el paso de parámetros en Java se hace de dos formas:
- Si se tratan de tipos primitivos como int, double, etc. el paso se da por valor o copia.
- Si se tratan de Objetos (en realidad son referencias a objetos) entonces el paso de valor se hace por referencia.
NO hay nada más equivocado que esta idea, lo lamentable es que incluso sean los autores de libros, los “conocedores” y expertos de la materia los que caigan en tan infantil error. Uno de los autores de los que hablo es un Español muy conocido cuyo nombre empieza con F…. otro autor que me parece es mexicano y si bien recuerdo es de la misma editorial que el primer autor que menciono y cuyo apellido también empieza con la letra F afirma del mismo modo que Java hace el paso de parámetros por referencia y cuyo libro/tutorial esta pegado en la página de un Instituto Tecnológico de aqui en México.
Y bueno ni se digan de varias páginas en donde se habla de lo mismo, por ejemplo: http://es.wikibooks.org
En fin, encontré un artículo que me parecio interesante: http://jpangamarca.wordpress.com/cafe-java/en-java-el-paso-de-parametros-es-por-valor/
donde desmiente ese mito de que Java hace el paso de parámetros por Referencia, dejando en claro que únicamente se hace por VALOR.
Si alguno tiene dudas sobre este tema de las Referencias de Objetos, comentela aqui y en la medida de mi tiempo trataré de brindarle alguna explicación.
NOTA DEL DÍA 29 DE JUNIO DEL 2009.
Dada la discución y confusión que existe en los comentarios de este tema, escribi un artículo dividido en tres partes en donde demuestro de forma contundente que Java no realiza un paso de parámetros por referencia.
Espero que con esto, quede aclarado todo este tema. Principalmente hubieron algunas personas que me acusaron de no tener idea de lo que digo
… pero bueno, este artículo les demuestra lo contrario.
http://mundobyte.wordpress.com/2009/06/29/i-paso-de-parmetros-en-java-por-valor/
Saludos!!
Archivado bajo: Java | Etiquetado: Parámetros Java, Valor o Referencia
Bueno, depende como se lo interprete. Los objetos sí se pasan por referencia, lo que se pasa por valor es la referencia al objeto.
Igual estyo de acuerdo en que es bueno aclarar todo eso y no dar una visión parcial que puede llevar a confusiones.
Cuando se pasa un parámetro a otro método se hace una copia de la referencia y NO se le pasa la dirección de memoria (que es a lo que llamamos paso por referencia), pues si esto ultimo fuera verdad el siguiente método modificaria el valor original…
public static void intercambiar(Empleado x, Empleado y)
{
Empleado temp = x;
x = y;
y = temp;
}
……
Empleado a = new Empleado(”Alicia”….);
Empleado b = new Empleado(”Benito…);
intercambiar(a,b)
¿Se refiere ahora “a” a Benito y b a alicia?… NO
Pero como se trata de una COPIA de la referencia al objeto, unicamente se modifica la copia y no el original. SI se tratara de un paso por referencia, ambos serían el mismo objeto en si, por lo cual, al tratar de referenciar:
x = y …. entonces también “temp” apuntaria al mismo objeto y por lo cual si habría una modificación al objeto original.
saludos!!
Ja…, yo creía lo mismo de que solo era paso por valor. Pero que gran mentira y ese artículo si que es una farsa. Acomodado y utilizando objetos diferentes para confundir. La realidad es que JAVA si permite paso por referencia. Es puro manejo de punteros. Solo en los tipos primitivos y String en el paso de argumentos a métodos se maneja el paso por valor…, para cualquier otro objeto que no sea String se pasa es la referencia, ósea se le asigna el valor de la referencia a otra referencia. Ambas quedan apuntando al mismo objeto y con la segunda puedo modificar el objeto…, Según el mismo principio que allí explican eso es paso por referencia…, Y lo debato con quien sea…
SI quiere debatirlo con quien sea, usted debe ser más inteligente que el mismo
James GOsling creador del lenguaje Java, quien realmente afirma que java
sol tiene un paso de parámetros, y es por valor….
Será que habrá que comparar curriculums para creer que usted es mejor y
tiene la razón??
Gracias por referenciar mi artículo. Saludos.
he leido este articulo pero en parte tienen razon pero por otra parte están en un error fatal, pues es asi como lo aprecio y les dire el por qué.
windoctor, segun el link y primer comentario, afirma que los objetos se pasan por valor y no por referencia.
si observa el metodo…
10 public static void cambiarObjeto(ValorOReferencia objeto) {
11 objeto = new ValorOReferencia(”Este es un nuevo objeto.”);
12 System.out.println(”Luego de \”reasignar\” pass: ” + objeto);
13 }
en la linea 10, el método crea una variable “objeto” de tipo “ValorOReferencia” que apunta precisamente a la misma dirección de memoria. Dicha direccion de memoria (pass=direccion de memoria xyz, objeto=direccion de memoria xyz).
Pero NOTESE que en la linea 11 asignamos con la funcion “new” una nueva direccion de memoria a la que apuntara “objeto”, por lo cual, a partir de este momento, objeto y memoria ya no apuntan a la misma direccion de memoria.
Concluyo que NO ES VALIDO el tratar de afirmar que los parametros de objetos se hacen por VALOR.
Con respecto a tu segundo comentario, windoctor, ese ejemplo me indica que tienes un concepto erroneo de como funcionan internamente los objetos, es decir, que sucede en memoria al declarar una variable de tipo “clase” y que sucede en memoria cuando se le aplica la funcion “new” a ese objeto.
Al declarar una variable de tipo “clase”, en memoria reserva una localidad de memoria para almacenar en ella un valor que hace referencia a otra localidad de memoria.
Cuando se aplica un “new” sobre una variable instanciada (”objeto”) de una clase, en memoria se reserva el tamaño del objeto para almacenar los valores de las propiedades del objeto, el cual sera referenciado por dicha variable instanciada (”objeto”).
Analiza tu ejemplo bajo la siguiente suposicion de direcciones de memoria:
“a” apunta a la dir. de mem. #AA
“b” apunta a la dir. de mem. #BB
El método intercambiar, al ser invocado, declara dos variables del mismo tipo que “a” y “b” llamadas “x” y “y”. Por lo tanto, “x” apunta a la dir. de mem. #AA y “y” apunta a #BB.
La línea de “Empleado temp=x” hace lo siguiente: en memoria se reserva una localidad de memoria para “x” la cual almacenará una dir. de mem. que corresponde a un objeto de tipo “Empleado”; es decir, “temp” apunta a la dir. de mem. #AA.
“x=y” hace que “x” apunte a la dir. de mem. #BB
“y=temp” hace que “y” apunte a la dir. de mem. #AA, y al terminar el método, elimina la variable “temp” pero no el objeto, debido a que la dir. de mem. que tenía almacenada (#AA) esta referenciada por el objeto “y”.
Ojo: “Asignación de objetos” no implica copiar las propiedades del objeto, solo implica que se asigna la misma referencia de mem. a la asignación de variable.
De hecho y sin crear polèmica, me parece que en lo personal yo aprecio en usted na confusión incluso entre lo que es una clase y un objeto asi como su representacion en memoria.
EL ejemplo que comentè, es del LIbro de Core Java de los autores Cay S. Horstmann y Gary Cornel, ambos cientificos respetables y consultores de Tecnologia Java.
EN su libro tratan todo este tema que merece la pena analizar.
LO malo que no tengo mucho tiempo de momento.
saludos!
windoctor ………claramente estas hablando de algo que poco o nada entiendes.
Hola!!!
Siguiendo su caso les quería comentar lo siguiente:
Definitivamente, cuando pasamos por parámetro un Objeto (Java), lo que pasa por valor es la dir. de memoria en donde esta alojado el mismo.
O sea el metodo “intercambiar(….)” antes mencionado, intercambia las referencias de las instancias pasadas por valor, pero al terminar la ejecución del metodo y volver al contexto de ejecución que invocó al metodo, los objetos que fueron como parametros del metodo “intercambiar(….)”, tendrán las dir. de memoria originales.
Saludos.
Les dejo un ejemplo:
/** Ejemplo —- Class**/
package oracle.tasa.pgc;
public class MemTest {
public class BaseIdDescDTO{
private String description;
public BaseIdDescDTO() {
super();
// TODO Auto-generated constructor stub
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
}
public BaseIdDescDTO getBaseInstance(){
return new BaseIdDescDTO();
}
public static void main(String []args){
BaseIdDescDTO b1 = new MemTest().getBaseInstance();
BaseIdDescDTO b2 = new MemTest().getBaseInstance();
b1.setDescription(”1111″);
b2.setDescription(”2222″);
System.out.println(”contenido antes: ” + b1.getDescription() + “, ” + b2.getDescription());
cambio(b1, b2);
System.out.println(”contenido despues: ” + b1.getDescription() + “, ” + b2.getDescription());
}
public static void cambio(BaseIdDescDTO x, BaseIdDescDTO y){
BaseIdDescDTO temp = x;
x = y;
y = temp;
y.setDescription(”3333″);
}
}
/** Fin class **/
__ Obtendrán como salida:
“contenido antes: 1111, 2222″
“contenido despues: 3333, 2222″
Windoctor. Dejame decirte que estas totalmente equivocado. Java si pasa parametros por referencia.
Tu haces referencia a
“En fin, encontré un artículo que me parecio interesante: http://jpangamarca.wordpress.com/cafe-java/en-java-el-paso-de-parametros-es-por-valor/“.
Dejame decirte que Juan Pablo Angamarca (el creador del articulo) no posee los conocimientos necesarios de Java, y si lees detalladamente el ejemplo te daras cuenta que en el ejemplo se describe exactamente el paso de parametros por referencia no por valor.
Lo que sucede es que tanto tu como Juan Pablo Angamarca parecen no haber trabajado nunca con el lenguaje C o C++, en donde se utilizaban punteros. los conocedores de estos lenguajes saben de lo que hablo, y sabran que Java viene de C y C++ y solo coloco una capa mas para manejar los punteros, para que los programadores no puedan apuntar a lugares que no corresponde (ya sea por que cometieron un error o no).
HOLA A TODOS!
DADA LA DISCUCIÓN Y CONFUSIÓN EXISTENTE EN ESTE TEMA, HE DECIDIDO ESCRIBIR UN ARTÍCULO DEMOSTRANDO EL ERROR QUE TIENEN MUCHOS AL PENSAR QUE JAVA HACE UN PASO DE PARÁMETROS POR REFERENCIA.
DIVIDO EL ARTÍCULO EN 3 PARTES, EN LA TERCERA PARTE PONGO REFERENCIAS REALES DE AUTORES QUE DESMIENTEN ESTE ERROR.
PRINCIPALMENTE PARA AQUELLOS QUE COMENTARON HACIA MI PERSONA DICIENDO QUE NO TENGO IDEA DE LO QUE HABLO, ESTE ARTÍCULO LES DEMOSTRARÁ EL ERROR EN EL QUE ESTAN.
SALUDOS!!
UPS! OLVIDE PONERLES EL VÍNCULO.
http://mundobyte.wordpress.com/2009/06/29/i-paso-de-parmetros-en-java-por-valor/
SALUDOS!!