Ir al contenido


Foto

Función que devuelve un objeto


  • Por favor identifícate para responder
7 respuestas en este tema

#1 jdepaz

jdepaz

    Advanced Member

  • Miembros
  • PipPipPip
  • 264 mensajes
  • LocationMedellín Colombia

Escrito 24 septiembre 2012 - 09:26

Hola y saludos a todos:

Tengo la siguiente clase, definida en la "unit2.pas"



delphi
  1. unit Unit2;
  2.  
  3. interface
  4.  
  5. type
  6. TEmpleado = Class
  7.     Constructor Create;
  8.     Destructor Destroy;override;
  9.   Private
  10.     FNombre: String;
  11.     FApellido: String;
  12.     Procedure SetNombre (Value: String);
  13.     Procedure SetApellido (Value: String);
  14.   Published
  15.     Property Nombre: String Read FNombre Write SetNombre;
  16.     Property Apellido: String Read FApellido Write SetApellido;
  17.  
  18. end;
  19.  
  20. implementation
  21.  
  22. procedure TEmpleado.SetNombre (Value: string);
  23. begin
  24.   FNombre:=Value;
  25. end;
  26. procedure TEmpleado.SetApellido (Value: string);
  27. begin
  28.   FApellido:=Value;
  29. end;
  30.  
  31. Constructor TEmpleado.Create;
  32. begin
  33.   inherited Create;
  34.  
  35. end;
  36.  
  37. Destructor TEmpleado.Destroy;
  38. begin
  39.   inherited Destroy;
  40. end;
  41.  
  42. end.




y la definición de otra clase, en la "uclassModelo.pas"



delphi
  1. unit uclassModelo;
  2.  
  3. interface
  4.  
  5. uses
  6.     unit2;
  7.  
  8.   type
  9.     TClassModelo = class
  10.     Public
  11.       function GetDatos:TEmpleado;
  12.     end;
  13.  
  14. implementation
  15.  
  16. function GetDatos:TEmpleado;
  17. var
  18.   objEmpleado:TEmpleado;
  19. begin
  20.   objEmpleado.Create;
  21.   result:=objEmpleado;
  22. end;
  23.  
  24. end.



Al realizar la compilación, me muestra el siguiente error:




delphi
  1. [DCC Error] uclassModelo.pas(11): E2065 Unsatisfied forward or external declaration: 'TClassModelo.GetDatos'




Creo que tengo deficiencias en OOP con respecto al lenguaje Pascal (por falta de práctica y uso)  :cry:,

¿Qué estoy haciendo de forma incorrecta?

Saludos


  • 0

#2 seoane

seoane

    Advanced Member

  • Administrador
  • 1.259 mensajes
  • LocationEspaña

Escrito 25 septiembre 2012 - 12:04

A simple vista, yo diría que el nombre de esta función:


delphi
  1. function GetDatos:TEmpleado;


deberia ser este otro:


delphi
  1. function TClassModelo.GetDatos:TEmpleado;


  • 0

#3 Wilson

Wilson

    Advanced Member

  • Moderadores
  • PipPipPip
  • 2.137 mensajes

Escrito 25 septiembre 2012 - 05:44

A primera vista, lo que encuentro mal sería esto:


delphi
  1. function GetDatos:TEmpleado;
  2. var
  3.   objEmpleado:TEmpleado;
  4. begin
  5.   objEmpleado.Create;
  6.   result:=objEmpleado;
  7. end;



Que deberías cambiarlo por esto:



delphi
  1. function GetDatos:TEmpleado;
  2. begin
  3.   result:=TEmpleado.Create;
  4. end;



Pero ojo que me quedan muchas dudas y cabos sueltos, por ejemplo ¿ Quien destruye todas las estancias de TEmpleado creadas a partir de la función GetDatos?

Aunque desconozco tus necesidades, yo creo que es más limpio y seguro crear una variable de TEmpleado cada que se ofrezca, realizar el proceso y finalmente liberarla, por ejemplo:



delphi
  1. procedure HacerAlgoConTEmpleado;
  2. var
  3. ObjEmpleado : TEmpleado;
  4. begin
  5. ObjEmpleado := TEmpleado.Create;
  6.   try
  7.   //Hacer cosas con el empleado
  8.   finally
  9.   ObjEmpleado.free
  10.   End;



Ahora si lo que necesitas es mantener una referencia global de una estancia de TEmpleado, bastaría en tu unit, crear un campo FEmpleado y asignarle un empleado en especial  cada que se te ofrezca, así tienes acceso permanente a un objeto de dicha clase.

Saludos.
  • 0

#4 Delphius

Delphius

    Advanced Member

  • Administrador
  • 6.295 mensajes
  • LocationArgentina

Escrito 25 septiembre 2012 - 07:07

La respuesta correcta es la suma se Seoane y Wilson  ;)

Cuando uno declara un método en una clase hace algo:



delphi
  1. TMiClase = class
  2. public
  3.   procedure MiMetodo(Param: integer);
  4. end;



Pero al momento de implementar es así:



delphi
  1. procedure TMiClase.MiMetodo(Param: integer);
  2. begin
  3.  
  4. end;



Justamente ese es uno de tus errores. Delphi te hace más fácil la vida y tiene una "macro" que te hace justamente la implementación de tus métodos. Una vez que defines las clase pulsa Crtl+Shift+C y gualá... en implementation tendrás la implementación de cada método. Solo te resta disponer el código dentro y declarar las variables que sean necesarias.

El otro error está en no hacer la construcción como debe:



delphi
  1. MiObjecto := TMiClase.Create;



Estos dos errores me dicen que antes estuviste en JAVA. ¿Puede ser?  ;)

Saludos,
  • 0

#5 poliburro

poliburro

    Advanced Member

  • Administrador
  • 4.945 mensajes
  • LocationMéxico

Escrito 25 septiembre 2012 - 07:07



delphi
  1. [DCC Error] uclassModelo.pas(11): E2065 Unsatisfied forward or external declaration: 'TClassModelo.GetDatos'




Creo que tengo deficiencias en OOP con respecto al lenguaje Pascal (por falta de práctica y uso)  :cry:,

¿Qué estoy haciendo de forma incorrecta?

Saludos




Lo que sucede es que no estas implementando correctamente el método GetEmpleado. Cómo dice seoane su implementación debe ser:



delphi
  1. function TClassModelo.GetDatos:TEmpleado;


  • 0

#6 jdepaz

jdepaz

    Advanced Member

  • Miembros
  • PipPipPip
  • 264 mensajes
  • LocationMedellín Colombia

Escrito 25 septiembre 2012 - 08:56

Gracias a todos,

Efectivamente, esta es la forma correcta (aunque el objeto dentro de la función tiene que tratarse de la forma correcta)



delphi
  1. unit uclassModelo;
  2.  
  3. interface
  4.  
  5. uses
  6.     unit2;
  7.  
  8.   type
  9.     TClassModelo = class
  10.     Public
  11.       function GetDatos:TEmpleado;
  12.     end;
  13.  
  14. implementation
  15.  
  16. function TClassModelo.GetDatos:TEmpleado;
  17. var
  18.   objEmpleado:TEmpleado;
  19. begin
  20.   objEmpleado.Create;
  21.   result:=objEmpleado;
  22. end;
  23.  
  24. end.



y con respecto:

Estos dos errores me dicen que antes estuviste en JAVA. ¿Puede ser?  ;)


Estas equivocado Chaparron, por cuestiones laborales, estoy en C++ y .Net, en Delphi tengo pocos desarrollos.

Actualmente estoy haciendo un ejercicio para implementar el Modelo Vista Presentador en Delphi.

Saludos


  • 0

#7 Sergio

Sergio

    Advanced Member

  • Moderadores
  • PipPipPip
  • 1.092 mensajes
  • LocationMurcia, España

Escrito 26 septiembre 2012 - 02:26

El código último que das sigue mal, por tu comentario creo que ya lo sabes, pero aclaro la diferencia entre las dos formas de usar el create, y las dos compilan sin error:

Forma "normal":


delphi
  1. objEmpleado:= TEmpleado.Create;



Esta es la que necesitas: crea el objeto y mete la referencia en tu variable.


Forma "rara":


delphi
  1. objEmpleado.Create;



Esta forma es "rara": supone que objEmpleado YA fue creado, pero que quieres "resetearlo" llamando de nuevo al procedure constructor, para el caso en que el constructor haga algún tipo de reinicialización que pueda ser repetido a mitad del proceso.

Se usa poco pero puede ser útil: si ademas de crear el objeto y iniciar sus sub-objetos luego haces un monton de cosas en tu create, puedes dejarlo preparado para poderse usar de esta forma detectando que los sub-objetos ya fueron creados -yo uso un flag boolean que fijo a true tras el primer create, como los boolean se crean a false tengo un control sobre si es la primera o la segunda vez que llamo al create- y saltarte esa parte y hacer solo la inicialización.

Es equivalente a que tu create haga la incialización "normal" y luego llame a un "create2", de forma que luego cuando quieres resetear el objeto llamas a objeto.create2 en lugar de objeto.create, con este truco "empaquetas" ambas cosas en un único create.



  • 0

#8 Delphius

Delphius

    Advanced Member

  • Administrador
  • 6.295 mensajes
  • LocationArgentina

Escrito 26 septiembre 2012 - 06:43

Estas equivocado Chaparron, por cuestiones laborales, estoy en C++ y .Net, en Delphi tengo pocos desarrollos.

Vaya, generalmente los que han estado en JAVA son lo que habitualmente cuando quieren migrar a Delphi les ha costado más acostumbrarse. Y dos de los errores típicos que a los que suelen enfrentarse son justamente a los que te has visto en tu código.

Tal como ha dicho Sergio, sigue estando mal... no estas creando apropiadamente el objeto. El compilador no reniega puesto que es válido hacer Obj.Create pero no es la forma más habitual y para que funcione se asume que efectivamente existe un objeto previamente creado. O es que se te olvidó o no estás prestando demasiada atención a nuestros comentarios.
Por otro lado no es necesario disponer de una variable para el método GetDatos. Ya dispones de result:



delphi
  1. function TClassModelo.GetDatos: TEmpleado;
  2. begin
  3.   result := TEmpleado.Create;
  4. end;



Saludos,
  • 0




IP.Board spam blocked by CleanTalk.