Distancia entre dos puntos
Definir la función
distancia :: (Double,Double) -> (Double,Double) -> Double
tal que (distancia p1 p2)
es la distancia entre los puntos p1
y p2
. Por ejemplo,
distancia (1,2) (4,6) == 5.0
Comprobar con QuickCheck que se verifica la propiedad triangular de la distancia; es decir, dados tres puntos p1
, p2
y p3
, la distancia de p1
a p3
es menor o igual que la suma de la distancia de p1
a p2
y la de p2
a p3
.
Soluciones
A continuación se muestran las soluciones en Haskell y las soluciones en Python.
Soluciones en Haskell
import Test.QuickCheck distancia :: (Double,Double) -> (Double,Double) -> Double distancia (x1,y1) (x2,y2) = sqrt((x1-x2)^2+(y1-y2)^2) -- La propiedad es prop_triangular :: (Double,Double) -> (Double,Double) -> (Double,Double) -> Property prop_triangular p1 p2 p3 = all acotado [p1, p2, p3] ==> distancia p1 p3 <= distancia p1 p2 + distancia p2 p3 where acotado (x, y) = abs x < cota && abs y < cota cota = 2^30 -- La comprobación es -- ghci> quickCheck prop_triangular -- +++ OK, passed 100 tests. -- Nota: Por problemas de redondeo, la propiedad no se cumple en -- general. Por ejemplo, -- λ> p1 = (0, 9147936743096483) -- λ> p2 = (0, 3) -- λ> p3 = (0, 2) -- λ> distancia p1 p3 <= distancia p1 p2 + distancia p2 p3 -- False -- λ> distancia p1 p3 -- 9.147936743096482e15 -- λ> distancia p1 p2 + distancia p2 p3 -- 9.14793674309648e15
El código se encuentra en GitHub.
Soluciones en Python
from math import sqrt from hypothesis import given, strategies as st def distancia(p1: tuple[float, float], p2: tuple[float, float]) -> float: (x1, y1) = p1 (x2, y2) = p2 return sqrt((x1-x2)**2+(y1-y2)**2) # La propiedad es cota = 2 ** 30 @given(st.tuples(st.integers(min_value=0, max_value=cota), st.integers(min_value=0, max_value=cota)), st.tuples(st.integers(min_value=0, max_value=cota), st.integers(min_value=0, max_value=cota)), st.tuples(st.integers(min_value=0, max_value=cota), st.integers(min_value=0, max_value=cota))) def test_triangular(p1, p2, p3): assert distancia(p1, p3) <= distancia(p1, p2) + distancia(p2, p3) # La comprobación es # src> poetry run pytest -q distancia_entre_dos_puntos.py # 1 passed in 0.38s # Nota: Por problemas de redondeo, la propiedad no se cumple en # general. Por ejemplo, # λ> p1 = (0, 9147936743096483) # λ> p2 = (0, 3) # λ> p3 = (0, 2) # λ> distancia(p1, p3) <= distancia(p1, p2) + distancia (p2. p3) # False # λ> distancia(p1, p3) # 9147936743096482.0 # λ> distancia(p1, p2) + distancia(p2, p3) # 9147936743096480.05
El código se encuentra en GitHub.
Comentarios
- La raíz cuadrada de
x
se escribe - en Haskell, como
sqrt x
y - en Python, como
sqrt(x)
y hay que importarla del módulomath
.