martes, 29 de enero de 2008

Nuevo en Delphi #2: Sobrecarga de operadores

Esta característica, aunque no añade funcionalidad, es simple pero poderosa en la legibilidad del código. La sobrecarga de operadores solo funciona en Records en Delphi win32 y para Records y Classes en Delphi.Net.

La sobrecarga de operadores consiste en poder definir un metodo de clase declarado como class operator, que se ejecuta cuando se utiliza dicho operador con ciertas clases como operandos, es decir que si definimos:

var
TTequila
= record
public
VolumenMiliLitros: integer;
GradoAlcohol: Single;
class operator Add(
TeqA, TeqB: TTequila): TTequila;
class operator GreaterThan(
TeqA, TeqB: TTequila): Boolean;
end;

class operator TTequila.Add(
TeqA, TeqB: TTequila): TTequila;
var
porcentAEnMezcla, porcentBEnMezcla: single;
begin
// Al mezclar (sumar) dos tequilas se obtiene
// la suma de su volumen liquido...
Result.VolumenMiliLitros :=
TeqA.VolumenMiliLitros
+TeqBVolumenMiliLitros;
// ...pero se promediaria su grado de alcohol
// en proporcion al volumen (en teoria)
porcentAEnMezcla :=
TeqA.VolumenMiliLitros
/Result.VolumenMiliLitros;
porcentBEnMezcla :
=
TeqB.VolumenMiliLitros
/Result.VolumenMiliLitros;
Result.GradoAlcohol :
=
(TeqA.GradoAlcohol
* porcentAEnMezcla) +
(TeqB.GradoAlcohol
* porcentBEnMezcla);
end;

class operator TTequila.GreaterThan(
TeqA, TeqB: TTequila): Boolean;
begin
if TeqA.GradoAlcohol > TeqB.GradoDeAlcohol then
Result :
= True
else
Result :
= False;
// Tambien podria ser:
// Result := (
// TeqA.GradoDeAlcohol > TeqB.GradoDeAlcohol);
end;


Entonces cuando tuvieramos algo como esto:


var
Jimador, Cazadores: TTequila;
MezclaChafa: TTequila;

begin
Jimador.VolumenMiliLitros :
= 750;
Jimador.GradoDeAlcohol :
= 30;

Cazadores.VolumenMiliLitros :
= 1000;
Cazadores.GradoDeAlcohol :
= 36;

if Cazadores > Jimador then
begin
MezclaChafa :
= Jimador + Cazadores
end
else
begin
MezclaChafa.VolumenMiliLitros :
= 0;
MezclaChafa.GradoDeAlcohol :
= 0;
end;

WriteLn(
'Mezclado ');
WriteLn(
'Volumen: ',
IntToStr(MezclaChafa.VolumenMiliLitros));
WriteLn(
'Grado De Alcohol: ',
FloatToStr(MezclaChafa.GradoDeAlcohol));
end;


El resultado seria:


Mezclado
Volumen: 1750
Grado De Alcohol: 33.4285


Ya que el operador Mayor Que > (GreaterThan) fue sobrecargado para que cuando se desea saber si un TTequila es mayor que otro TTequila (los dos parámetros del operator son TTequila) entonces devuelve Verdadero si el primer TTequila tiene un GradoAlcohol mayor que el otro.


De igual manera, el operador Adición, o Suma + (Add) fue sobrecargado para que cuando se "suman" dos TTequila, el resultado sea otro TTequila con la suma de los volumenes y el proporcional del grado de alcohol de cada uno según el volumen que aportan.


NOTA IMPORTANTE: Otra relativamente "reciente" característica de Delphi es precisamente que los tipos record pueden tener métodos como las clases, con la diferencia que los record son pasados por valor (una copia de ellos) y las clases por referencia (una copia del apuntador hacia la clase).

No hay comentarios.:

Publicar un comentario