Práctica: Números Fraccionarios

Construya un módulo que permita el uso de números fraccionarios como $ \frac{4}{5}, \frac{2}{9}, \ldots$, etc. y las operaciones habituales entre los mismos.



Subsecciones

Lenguajes y Herramientas de Programacion 2011-02-02
produce la siguiente salida:
$ ./fractions2.pl
t=1/1, ref(t)=Number::Fraction
x=1/2, ref(x)=Number::Fraction
¿Porqué la asignación de la línea 5 ($x = $t) no parece comportarse como una asignación de referencias como se señaló en la sección anterior?. La modificación de $t no produce un efecto lateral sobre $x. Nótese que el operador = no ha sido sobrecargado en Number::Fraction. Puede comprobarlo en el listado de la cabecera de Number::Fraction que aparece en la sección 6.8.3 pagina [*].

Para ayudar a entender lo que esta ocurriendo, aqui tiene el código del método add que sobrecarga el operador +

sub add {
  my ($l, $r, $rev) = @_;

  if (ref $r) {
    if (UNIVERSAL::isa($r, ref $l)) { # Ambos heredan de ref $l
      return (ref $l)->new( # Puede que 'new' hay sido sobreescrito
                           $l->{num} * $r->{den} + $r->{num} * $l->{den},
			   $r->{den} * $l->{den}
                          );
    } else {
      croak "Can't add a ", ref $l, " to a ", ref $r;
    }
  } else {
    if ($r =~ /^[-+]?\d+$/) { # $r es un número entero
      return $l + (ref $l)->new($r, 1);
    } else { # r es un double: convertimos
      return $l->to_num + $r;
    }
  }
}

Lenguajes y Herramientas de Programacion 2011-02-03