| rs a |
rs := ReadStream on: 'Mary had a little `laptop, its screen was white as snow'.
a := rs upTo: $`.
Transcript show: a printString
main = print . length . show $ prod 100000
prod n = p 1 1
where p start step
| start + step > n = start
| otherwise = let step' = 2 * step
in p start step' * p (start + step) step'
% ---------------------------------------------------------------- Movimientos posibles
% Invierte la direcciÛn del movimiento anterior
nuevomovimiento(oeste, este).
% Invierte la direcciÛn del movimiento anterior
nuevomovimiento(este, oeste).
% Se mueve el Granjero, pasando de X a Y con el Zorro
% Movido = Zorro
mover(Tipos, Estados1, Estados2, Movimiento) :-
comparar(Estados1, Estados2, 2), % Verifica que solamente se hayan movido dos elementos
buscar(Tipos, 1, B), % Busca la posicion B segun el tipo 1 (Zorro)
posicion(B, Estados1, X), % Busca el estado del elemento en B (Zorro)
posicion(B, Estados2, Y), % Busca el estado del elemento en B (Zorro)
buscar(Tipos, 4, C), % Busca la posicion C segun el tipo 4 (Granjero)
posicion(C, Estados1, X), % Busca el estado del elemento en C (Granjero)
posicion(C, Estados2, Y), % Busca el estado del elemento en C (Granjero)
nuevomovimiento(X, Y),
Movimiento = [zorro, Y].
% Se mueve el Granjero, pasando de X a Y con la Oca
% Movido = Oca
mover(Tipos, Estados1, Estados2, Movimiento):-
comparar(Estados1, Estados2, 2), % Verifica que solamente se hayan movido dos elementos
buscar(Tipos, 2, B), % Busca la posicion B segun el tipo 2 (Oca)
posicion(B, Estados1, X),% Busca el estado del elemento en B (Oca)
posicion(B, Estados2, Y),% Busca el estado del elemento en B (Oca)
buscar(Tipos, 4, C), % Busca la posicion C segun el tipo 4 (Granjero)
posicion(C, Estados1, X),% Busca el estado del elemento en C (Granjero)
posicion(C, Estados2, Y),% Busca el estado del elemento en C (Granjero)
nuevomovimiento(X, Y),
Movimiento = [oca, Y].
% Se mueve el Granjero, pasando de X a Y con el Grano
% Movido = Grano
mover(Tipos, Estados1, Estados2, Movimiento):-
comparar(Estados1, Estados2, 2), % Verifica que solamente se hayan movido dos elementos
buscar(Tipos, 3, B), % Busca la posicion B segun el tipo 3 (Grano)
posicion(B, Estados1, X),% Busca el estado del elemento en B (Grano)
posicion(B, Estados2, Y),% Busca el estado del elemento en B (Grano)
buscar(Tipos, 4, C), % Busca la posicion C segun el tipo 4 (Granjero)
posicion(C, Estados1, X),% Busca el estado del elemento en C (Granjero)
posicion(C, Estados2, Y),% Busca el estado del elemento en C (Granjero)
nuevomovimiento(X, Y),
Movimiento = [grano, Y].
% Se mueve el Granjero, pasando de X a Y solo sin nada
% Movido = Nada
mover(Tipos, Estados1, Estados2, Movimiento) :-
comparar(Estados1, Estados2, 1), % Verifica que solamente se haya movido un elemento
buscar(Tipos, 4, C), % Busca la posicion C segun el tipo 4 (Granjero)
posicion(C, Estados1, X),% Busca el estado del elemento en C (Granjero)
posicion(C, Estados2, Y),% Busca el estado del elemento en C (Granjero)
nuevomovimiento(X, Y),
Movimiento = [nada, Y].
/*
% Se mueve el Granjero, pasando de X a Y con otro Granjero
% Movido = Granjeros
mover(Tipos, Estados1, Estados2, Movimiento) :-
comparar(Estados1, Estados2, 2), % Verifica que solamente se hayan movido dos elementos
buscar(Tipos, 4, B), % Busca la posicion B segun el tipo 4 (Granjero)
posicion(B, Estados1, X), % Busca el estado del elemento en B (Granjero)
posicion(B, Estados2, Y), % Busca el estado del elemento en B (Granjero)
buscar(Tipos, 4, C), % Busca la posicion C segun el tipo 4 (Granjero)
posicion(C, Estados1, X), % Busca el estado del elemento en C (Granjero)
posicion(C, Estados2, Y), % Busca el estado del elemento en C (Granjero)
B \== C,
nuevomovimiento(X, Y),
Movimiento = [granjeroaux, Y].
*/
% ---------------------------------------------------------------- Estados inv·lidos
% Zorro 1, Oca 2, Grano 3, Granjero 4
% Es inv·lido que la Oca y la Bolsa se encuentren del mismo lado
% y que el Granjero se encuentre del otro lado
invalido(Tipos, Estados) :-
buscar(Tipos, 2, A), % Busca la posicion A segun el tipo 2 (Oca)
posicion(A, Estados, X), % Busca el estado del elemento en A (Oca)
buscar(Tipos, 3, B), % Busca la posicion B segun el tipo 3 (Grano)
posicion(B, Estados, X), % Busca el estado del elemento en B (Grano)
igualesportipo(Tipos,Estados,4, Y), % Busca si todos los granjeros est·n del lado Y
X \== Y.
% Es inv·lido que el Zorro y la Oca se encuentren del mismo lado
% y que el Granjero se encuentre del otro lado
invalido(Tipos, Estados) :-
buscar(Tipos, 1, A), % Busca la posicion A segun el tipo (Zorro)
posicion(A, Estados, X), % Busca el estado del elemento en A (Zorro)
buscar(Tipos, 2, B), % Busca la posicion B segun el tipo 2 (Oca)
posicion(B, Estados, X), % Busca el estado del elemento en B (Oca)
igualesportipo(Tipos,Estados,4, Y), % Busca si todos los granjeros est·n del lado Y
X \== Y.
% ---------------------------------------------------------------- Algoritmo de resolucion (recursivo)
% CondiciÛn de parada de la recursiÛn
% Todos las compras del granjero en el mismo lado destino
% Esto indica el fin del algoritmo y ya no se deben hacer movimientos adicionales
resolver(_, Estados, Dest, _, []) :-
iguales(Estados,Dest).
% Estado -> Estados actuales de los 4 elementos (Este u Oeste)
% Dest -> Lugar hacia donde tiene que llegar el movimiento
% N -> M·ximo de pasos restantes
% Recorrido -> Lista donde se van guardando los resultados
resolver(Tipos, Estados, Dest, N, Recorrido) :-
N > 0, % Todavia quedan pasos
mover(Tipos, Estados, NuevosEstados,[Animal, Direction]),% Se mueve del estado a NuevoEstado y el resultado queda en Animal y Direction
\+(invalido(Tipos, NuevosEstados)), % El NuevoEstado no es un estado inv·lido
resolver(Tipos, NuevosEstados, Dest, N-1, Cola), % NuevoEstado es el estado inicial del siguiente movimiento hacia el mismo destino
Recorrido = [pasar(Animal, Direction) | Cola]. % Recorrido une la respuesta del movimiento actual (Animal y Direction) con la respuesta de
% los siguientes movimientos
% X -> Todos empiezan en estado Oeste (obtenido con el temp)
% este -> Indica que tienen que moverse al Este
% 7 -> M·ximo de pasos a realizar
% R -> Guarda los pasos en la lista
iniciar(Tipos, Pasos, R) :-
maximo(N, Tipos),
inicializar(Estados, N, oeste),
resolver(Tipos, Estados, este, Pasos, R).
% ---------------------------------------------------------------- Otros predicados para el manejo de las listas y los estados
% Para saber la m·xima cantidad de items
maximo(0, []).
maximo(N, [_|Col]) :-
maximo(Nant,Col),
N is Nant + 1.
% Para inicializar los elementos en un valor
inicializar([], 0, _).
inicializar(Arreglo, Profundidad, Valor) :-
Profundidad > 0,
Arreglo = [Valor|Col],
ProfundidadAnt is Profundidad - 1,
inicializar(Col, ProfundidadAnt, Valor).
% Para saber si todos los elementos en la lista tienen el mismo valor
iguales([], _).
iguales([Cab|Col], Valor) :-
Cab == Valor,
iguales(Col, Valor).
% Para saber si todos los elementos con un tipo determinado tienen el mismo valor
tmpigualesportipo(Tipo,Valor,Tipo,Valor).
tmpigualesportipo(CabT,_,Tipo,_) :-
CabT \== Tipo.
igualesportipo([],[], _,_).
igualesportipo([CabT|ColT],[CabE|ColE], Tipo, Valor) :-
tmpigualesportipo(CabT,CabE,Tipo,Valor),
igualesportipo(ColT, ColE,Tipo,Valor).
% Para comparar dos n˙meros y dependiendo de si son iguales o no muestra un resultado.
evaluar(X, X, Entrada, Entrada).
evaluar(X, Y, Entrada, Salida) :-
X \== Y,
Salida is Entrada - 1.
% Para saber si existe un determinado n˙mero de cambios entre 2 listados
comparar([],[],MaxCambios) :-
MaxCambios >= 0.
comparar([Cab1|Col1],[Cab2|Col2],MaxCambios) :-
evaluar(Cab1, Cab2, MaxCambios, MaxCambiosSig),
comparar(Col1, Col2, MaxCambiosSig).
% Para encontrar el elemento en una posiciÛn epecifica
posicion(1,[Cab|_],Cab).
posicion(I,[_|Col],Elemento) :-
%posicion(I,[Cab|Col],Elemento) :-
%maximo(N,[Cab|Col]),
%I =< N,
Iant is I - 1,
posicion(Iant, Col, Elemento).
% Para buscar un elemento en la lista
buscar([Cab|_], Cab, 1).
buscar([_|Col], Elemento, I) :-
buscar(Col, Elemento, Iant),
I is Iant + 1.
% ---------------------------------------------------------------- Interfaz con el usuario
paso(I, Tipos, Pasos, Salida) :-
iniciar(Tipos, Pasos, R),
posicion(I, R, Salida).
listadopasos(Tipos, Pasos, Salida) :-
iniciar(Tipos, Pasos, Salida).
\sum_{3}^{2} \int \frac{1}{x}dx
Bueno finalmente encontre los brushes que decia.
Por favor revisen si tienen sentido o si se pueden mejorar los que tengan idea.
Gracias!