{"id":7794,"date":"2022-09-17T08:05:11","date_gmt":"2022-09-17T06:05:11","guid":{"rendered":"https:\/\/www.glc.us.es\/~jalonso\/vestigium\/?p=7794"},"modified":"2022-09-17T08:06:28","modified_gmt":"2022-09-17T06:06:28","slug":"pfh-la-semana-en-exercitium-16-de-septiembre-de-2022","status":"publish","type":"post","link":"https:\/\/www.glc.us.es\/~jalonso\/vestigium\/pfh-la-semana-en-exercitium-16-de-septiembre-de-2022\/","title":{"rendered":"PFH: La semana en Exercitium (16 de septiembre de 2022)"},"content":{"rendered":"<p>Esta semana he publicado en <a href=\"http:\/\/bit.ly\/2sqPtGs\">Exercitium<\/a> las soluciones de los siguientes problemas:<\/p>\n<ul>\n<li><a href=\"#ej1\">1. Ra\u00edces de la ecuaci\u00f3n de segundo grado<\/a><\/li>\n<li><a href=\"#ej2\">2. F\u00f3rmula de Her\u00f3n para el \u00e1rea de un tri\u00e1ngulo<\/a><\/li>\n<li><a href=\"#ej3\">3. Intersecci\u00f3n de intervalos cerrados<\/a><\/li>\n<li><a href=\"#ej4\">4. N\u00fameros racionales<\/a><\/li>\n<li><a href=\"#ej5\">5. Reconocimiento de subconjunto<\/a><\/li>\n<\/ul>\n<p>A continuaci\u00f3n se muestran las soluciones.<br \/>\n<!--more--><br \/>\n<a name=\"ej1\"><\/a><\/p>\n<h3>1. Ra\u00edces de la ecuaci\u00f3n de segundo grado<\/h3>\n<p>Definir la funci\u00f3n<\/p>\n<pre lang=\"text\">\n   raices :: Double -> Double -> Double -> [Double]\n<\/pre>\n<p>tal que <code>(raices a b c)<\/code> es la lista de las ra\u00edces reales de la ecuaci\u00f3n <img decoding=\"async\" src=\"https:\/\/s0.wp.com\/latex.php?latex=ax%5E2+%2B+bx+%2B+c+%3D+0&#038;bg=ffffff&#038;fg=000&#038;s=0&#038;c=20201002\" alt=\"ax^2 + bx + c = 0\" class=\"latex\" \/>. Por ejemplo,<\/p>\n<pre lang=\"text\">\n   raices 1 3 2    ==  [-1.0,-2.0]\n   raices 1 (-2) 1 ==  [1.0,1.0]\n   raices 1 0 1    ==  []\n<\/pre>\n<p>Comprobar con QuickCheck que la suma de las ra\u00edces de la ecuaci\u00f3n <img decoding=\"async\" src=\"https:\/\/s0.wp.com\/latex.php?latex=ax%5E2+%2B+bx+%2B+c+%3D+0&#038;bg=ffffff&#038;fg=000&#038;s=0&#038;c=20201002\" alt=\"ax^2 + bx + c = 0\" class=\"latex\" \/> (con <img decoding=\"async\" src=\"https:\/\/s0.wp.com\/latex.php?latex=a&#038;bg=ffffff&#038;fg=000&#038;s=0&#038;c=20201002\" alt=\"a\" class=\"latex\" \/> no nulo) es <img decoding=\"async\" src=\"https:\/\/s0.wp.com\/latex.php?latex=%5Cfrac%7B-b%7D%7Ba%7D&#038;bg=ffffff&#038;fg=000&#038;s=0&#038;c=20201002\" alt=\"&#92;frac{-b}{a}\" class=\"latex\" \/> y su  producto es <img decoding=\"async\" src=\"https:\/\/s0.wp.com\/latex.php?latex=%5Cfrac%7Bc%7D%7Ba%7D&#038;bg=ffffff&#038;fg=000&#038;s=0&#038;c=20201002\" alt=\"&#92;frac{c}{a}\" class=\"latex\" \/>.<\/p>\n<p><b>Soluciones en Haskell<\/b><\/p>\n<pre lang=\"haskell\">\nimport Test.QuickCheck\n\nraices :: Double -> Double -> Double -> [Double]\nraices a b c\n    | d >= 0    = [(-b+e)\/t,(-b-e)\/t]\n    | otherwise = []\n    where d = b^2 - 4*a*c\n          e = sqrt d\n          t = 2*a\n\n-- Para comprobar la propiedad se usar\u00e1 el operador\n--    (~=) :: (Fractional a, Ord a) => a -> a -> Bool\n-- tal que (x ~= y) se verifica si x e y son casi iguales; es decir si\n-- el valor absoluto de su diferencia es menor que una mil\u00e9sima. Por\n-- ejemplo,\n--    12.3457 ~= 12.3459  ==  True\n--    12.3457 ~= 12.3479  ==  False\n(~=) :: (Fractional a, Ord a) => a -> a -> Bool\nx ~= y  = abs (x-y) < 0.001\n\n-- La propiedad es\nprop_raices :: Double -> Double -> Double -> Property\nprop_raices a b c =\n    a \/= 0 && not (null xs) ==> sum xs ~= (-b\/a) && product xs ~= (c\/a)\n    where xs = raices a b c\n\n-- La comprobaci\u00f3n es\n--    \u03bb> quickCheck prop_raices\n--    +++ OK, passed 100 tests.\n<\/pre>\n<p>El c\u00f3digo se encuentra en <a href=\"https:\/\/github.com\/jaalonso\/Exercitium\/blob\/main\/src\/Raices_de_la_ecuacion_de_segundo_grado.hs\">GitHub<\/a>.<\/p>\n<p><b>Soluciones en Python<\/b><\/p>\n<pre lang=\"python\">\nfrom math import sqrt\nfrom hypothesis import given, assume, strategies as st\n\ndef raices(a: float, b: float, c: float) -> list[float]:\n    d = b**2 - 4*a*c\n    if d >= 0:\n        e = sqrt(d)\n        t = 2*a\n        return [(-b+e)\/t, (-b-e)\/t]\n    return []\n\n# Para comprobar la propiedad se usar\u00e1 la funci\u00f3n\n#    casiIguales : (float, float) -> bool\n# tal que casiIguales(x, y) se verifica si x e y son casi iguales; es\n# decir si el valor absoluto de su diferencia es menor que una\n# mil\u00e9sima. Por  ejemplo,\n#    casiIguales(12.3457, 12.3459)  ==  True\n#    casiIguales(12.3457, 12.3479)  ==  False\ndef casiIguales(x: float, y: float) -> bool:\n    return abs(x - y) < 0.001\n\n# La propiedad es\n@given(st.floats(min_value=-100, max_value=100),\n       st.floats(min_value=-100, max_value=100),\n       st.floats(min_value=-100, max_value=100))\ndef test_prop_raices(a, b, c):\n    assume(abs(a) > 0.1)\n    xs = raices(a, b, c)\n    assume(xs)\n    [x1, x2] = xs\n    assert casiIguales(x1 + x2, -b \/ a)\n    assert casiIguales(x1 * x2, c \/ a)\n\n# La comprobaci\u00f3n es\n#    src> poetry run pytest -q raices_de_la_ecuacion_de_segundo_grado.py\n#    1 passed in 0.35s\n<\/pre>\n<p>El c\u00f3digo se encuentra en <a href=\"https:\/\/github.com\/jaalonso\/Exercitium-Python\/blob\/main\/src\/raices_de_la_ecuacion_de_segundo_grado.py\">GitHub<\/a>.<\/p>\n<p><a name=\"ej2\"><\/a><\/p>\n<h3>2. F\u00f3rmula de Her\u00f3n para el \u00e1rea de un tri\u00e1ngulo<\/h3>\n<p>La f\u00f3rmula de Her\u00f3n, descubierta por Her\u00f3n de Alejandr\u00eda, dice que el \u00e1rea de un tri\u00e1ngulo cuyo lados miden a, b y c es la ra\u00edz cuadrada de s(s-a)(s-b)(s-c) donde s es el semiper\u00edmetro<\/p>\n<pre lang=\"text\">\n   s = (a+b+c)\/2\n<\/pre>\n<p>Definir la funci\u00f3n<\/p>\n<pre lang=\"text\">\n   area :: Double -> Double -> Double -> Double\n<\/pre>\n<p>tal que <code>(area a b c)<\/code> es el \u00e1rea del tri\u00e1ngulo de lados <code>a<\/code>, <code>b<\/code> y <code>c<\/code>. Por ejemplo,<\/p>\n<pre lang=\"text\">\n   area 3 4 5  ==  6.0\n<\/pre>\n<p><b>Soluciones en Haskell<\/b><\/p>\n<pre lang=\"haskell\">\narea :: Double -> Double -> Double -> Double\narea a b c = sqrt (s*(s-a)*(s-b)*(s-c))\n  where s = (a+b+c)\/2\n<\/pre>\n<p>El c\u00f3digo se encuentra en <a href=\"https:\/\/github.com\/jaalonso\/Exercitium\/blob\/main\/src\/Formula_de_Heron_para_el_area_de_un_triangulo.hs\">GitHub<\/a>.<\/p>\n<p><b>Soluciones en Python<\/b><\/p>\n<pre lang=\"python\">\nfrom math import sqrt\n\ndef area(a: float, b: float, c: float) -> float:\n    s = (a+b+c)\/2\n    return sqrt(s*(s-a)*(s-b)*(s-c))\n<\/pre>\n<p>El c\u00f3digo se encuentra en <a href=\"https:\/\/github.com\/jaalonso\/Exercitium-Python\/blob\/main\/src\/formula_de_Heron_para_el_area_de_un_triangulo.py\">GitHub<\/a>.<\/p>\n<p><a name=\"ej3\"><\/a><\/p>\n<h3>3. Intersecci\u00f3n de intervalos cerrados<\/h3>\n<p>Los intervalos cerrados se pueden representar mediante una lista de dos n\u00fameros (el primero es el extremo inferior del intervalo y el segundo el superior).<\/p>\n<p>Definir la funci\u00f3n<\/p>\n<pre lang=\"text\">\n   interseccion :: Ord a => [a] -> [a] -> [a]\n<\/pre>\n<p>tal que <code>(interseccion i1 i2)<\/code> es la intersecci\u00f3n de los intervalos <code>i1<\/code> e <code>i2<\/code>. Por ejemplo,<\/p>\n<pre lang=\"text\">\n   interseccion [] [3,5]     ==  []\n   interseccion [3,5] []     ==  []\n   interseccion [2,4] [6,9]  ==  []\n   interseccion [2,6] [6,9]  ==  [6,6]\n   interseccion [2,6] [0,9]  ==  [2,6]\n   interseccion [2,6] [0,4]  ==  [2,4]\n   interseccion [4,6] [0,4]  ==  [4,4]\n   interseccion [5,6] [0,4]  ==  []\n<\/pre>\n<p>Comprobar con QuickCheck que la intersecci\u00f3n de intervalos es conmutativa.<\/p>\n<p><b>Soluciones en Haskell<\/b><\/p>\n<pre lang=\"haskell\">\nimport Test.QuickCheck\n\ninterseccion :: Ord a => [a] -> [a] -> [a]\ninterseccion [] _ = []\ninterseccion _ [] = []\ninterseccion [a1,b1] [a2,b2]\n    | a <= b    = [a,b]\n    | otherwise = []\n    where a = max a1 a2\n          b = min b1 b2\n\n-- La propiedad es\nprop_interseccion :: Int -> Int -> Int -> Int -> Property\nprop_interseccion a1 b1 a2 b2 =\n  a1 <= b1 &#038;&#038; a2 <= b2 ==>\n  interseccion [a1,b1] [a2,b2] == interseccion [a2,b2] [a1,b1]\n\n-- La comprobaci\u00f3n es\n--    \u03bb> quickCheck prop_interseccion\n--    +++ OK, passed 100 tests; 263 discarded.\n<\/pre>\n<p>El c\u00f3digo se encuentra en <a href=\"https:\/\/github.com\/jaalonso\/Exercitium\/blob\/main\/src\/Interseccion_de_intervalos_cerrados.hs\">GitHub<\/a>.<\/p>\n<p><b>Soluciones en Python<\/b><\/p>\n<pre lang=\"python\">\nfrom hypothesis import given, assume, strategies as st\n\nRectangulo = list[float]\n\ndef interseccion(i1: Rectangulo,\n                 i2: Rectangulo) -> Rectangulo:\n    if i1 and i2:\n        [a1, b1] = i1\n        [a2, b2] = i2\n        a = max(a1, a2)\n        b = min(b1, b2)\n        if a <= b:\n            return [a, b]\n        return []\n    return []\n\n# La propiedad es\n@given(st.floats(), st.floats(), st.floats(), st.floats())\ndef test_prop_raices(a1, b1, a2, b2):\n    assume(a1 <= b1 and a2 <= b2)\n    assert interseccion([a1, b1], [a2, b2]) == interseccion([a2, b2], [a1, b1])\n\n# La comprobaci\u00f3n es\n#    src> poetry run pytest -q interseccion_de_intervalos_cerrados.py\n#    1 passed in 0.64s\n<\/pre>\n<p>El c\u00f3digo se encuentra en <a href=\"https:\/\/github.com\/jaalonso\/Exercitium-Python\/blob\/main\/src\/interseccion_de_intervalos_cerrados.py\">GitHub<\/a>.<\/p>\n<p><a name=\"ej4\"><\/a><\/p>\n<h3>4. N\u00fameros racionales<\/h3>\n<p>Los n\u00fameros racionales pueden representarse mediante pares de n\u00fameros enteros. Por ejemplo, el n\u00famero 2\/5 puede representarse mediante el par (2,5).<\/p>\n<p>Definir las funciones<\/p>\n<pre lang=\"text\">\n   formaReducida    :: (Int,Int) -> (Int,Int)\n   sumaRacional     :: (Int,Int) -> (Int,Int) -> (Int,Int)\n   productoRacional :: (Int,Int) -> (Int,Int) -> (Int,Int)\n   igualdadRacional :: (Int,Int) -> (Int,Int) -> Bool\n<\/pre>\n<p>tales que<\/p>\n<ul>\n<li><code>formaReducida x<\/code> es la forma reducida del n\u00famero racional <code>x<\/code>. Por ejemplo,<\/li>\n<\/ul>\n<pre lang=\"text\">\n     formaReducida (4,10)  ==  (2,5)\n     formaReducida (0,5)   ==  (0,1)\n<\/pre>\n<ul>\n<li><code>sumaRacional x y<\/code> es la suma de los n\u00fameros racionales <code>x<\/code> e <code>y<\/code>, expresada en forma reducida. Por ejemplo,<\/li>\n<\/ul>\n<pre lang=\"text\">\n     sumaRacional (2,3) (5,6)  ==  (3,2)\n     sumaRacional (3,5) (-3,5) ==  (0,1)\n<\/pre>\n<ul>\n<li><code>productoRacional x y<\/code> es el producto de los n\u00fameros racionales <code>x<\/code> e <code>y<\/code>, expresada en forma reducida. Por ejemplo,<\/li>\n<\/ul>\n<pre lang=\"text\">\n     productoRacional (2,3) (5,6)  ==  (5,9)\n<\/pre>\n<ul>\n<li><code>igualdadRacional x y<\/code> se verifica si los n\u00fameros racionales <code>x<\/code> e <code>y<\/code> son iguales. Por ejemplo,<\/li>\n<\/ul>\n<pre lang=\"text\">\n     igualdadRacional (6,9) (10,15)  ==  True\n     igualdadRacional (6,9) (11,15)  ==  False\n     igualdadRacional (0,2) (0,-5)   ==  True\n<\/pre>\n<p>Comprobar con QuickCheck la propiedad distributiva del producto racional respecto de la suma.<\/p>\n<p><b>Soluciones en Haskell<\/b><\/p>\n<pre lang=\"haskell\">\nimport Test.QuickCheck\n\nformaReducida :: (Int,Int) -> (Int,Int)\nformaReducida (0,_) = (0,1)\nformaReducida (a,b) = (a `div` c, b  `div` c)\n    where c = gcd a b\n\nsumaRacional :: (Int,Int) -> (Int,Int) -> (Int,Int)\nsumaRacional (a,b) (c,d) = formaReducida (a*d+b*c, b*d)\n\nproductoRacional :: (Int,Int) -> (Int,Int) -> (Int,Int)\nproductoRacional (a,b) (c,d) = formaReducida (a*c, b*d)\n\nigualdadRacional :: (Int,Int) -> (Int,Int) -> Bool\nigualdadRacional (a,b) (c,d) =\n    a*d == b*c\n\n-- La propiedad es\nprop_distributiva :: (Int,Int) -> (Int,Int) -> (Int,Int) -> Property\nprop_distributiva x y z =\n  snd x \/= 0 && snd y \/= 0 && snd z \/= 0 ==>\n  igualdadRacional (productoRacional x (sumaRacional y z))\n                   (sumaRacional (productoRacional x y)\n                                 (productoRacional x z))\n\n-- La comprobaci\u00f3n es\n--    \u03bb> quickCheck prop_distributiva\n--    +++ OK, passed 100 tests; 21 discarded.\n<\/pre>\n<p>El c\u00f3digo se encuentra en <a href=\"https:\/\/github.com\/jaalonso\/Exercitium\/blob\/main\/src\/Numeros_racionales.hs\">GitHub<\/a>.<\/p>\n<p><b>Soluciones en Python<\/b><\/p>\n<pre lang=\"python\">\nfrom math import gcd\nfrom hypothesis import given, assume, strategies as st\n\nRacional = tuple[int, int]\n\ndef formaReducida(x: Racional) -> Racional:\n    (a, b) = x\n    if a == 0:\n        return (0, 1)\n    c = gcd(a, b)\n    return (a \/\/ c, b \/\/ c)\n\ndef sumaRacional(x: Racional,\n                 y: Racional) -> Racional:\n    (a, b) = x\n    (c, d) = y\n    return formaReducida((a*d+b*c, b*d))\n\ndef productoRacional(x: Racional,\n                     y: Racional) -> Racional:\n    (a, b) = x\n    (c, d) = y\n    return formaReducida((a*c, b*d))\n\ndef igualdadRacional(x: Racional,\n                     y: Racional) -> bool:\n    (a, b) = x\n    (c, d) = y\n    return a*d == b*c\n\n# La propiedad es\n@given(st.tuples(st.integers(), st.integers()),\n       st.tuples(st.integers(), st.integers()),\n       st.tuples(st.integers(), st.integers()))\ndef test_prop_distributiva(x, y, z):\n    (_, x2) = x\n    (_, y2) = y\n    (_, z2) = z\n    assume(x2 != 0 and y2 != 0 and z2 != 0)\n    assert igualdadRacional(productoRacional(x, sumaRacional(y, z)),\n                            sumaRacional(productoRacional(x, y),\n                                         productoRacional(x, z)))\n\n# La comprobaci\u00f3n es\n#    src> poetry run pytest -q numeros_racionales.py\n#    1 passed in 0.37s\n<\/pre>\n<p>El c\u00f3digo se encuentra en <a href=\"https:\/\/github.com\/jaalonso\/Exercitium-Python\/blob\/main\/src\/numeros_racionales.py\">GitHub<\/a>.<\/p>\n<p><a name=\"ej5\"><\/a><\/p>\n<h3>5. Reconocimiento de subconjunto<\/h3>\n<p>Definir la funci\u00f3n<\/p>\n<pre lang=\"text\">\n   subconjunto :: Ord a => [a] -> [a] -> Bool\n<\/pre>\n<p>tal que <code>subconjunto xs ys<\/code> se verifica si <code>xs<\/code> es un subconjunto de <code>ys<\/code>. por ejemplo,<\/p>\n<pre lang=\"text\">\n   subconjunto [3,2,3] [2,5,3,5]  ==  True\n   subconjunto [3,2,3] [2,5,6,5]  ==  False\n<\/pre>\n<p><b>Soluciones en Haskell<\/b><\/p>\n<pre lang=\"haskell\">\nmodule Reconocimiento_de_subconjunto where\n\nimport Data.List (nub, sort)\nimport Data.Set (fromList, isSubsetOf)\nimport Test.QuickCheck\n\n-- 1\u00aa soluci\u00f3n\nsubconjunto1 :: Ord a => [a] -> [a] -> Bool\nsubconjunto1 xs ys =\n  [x | x <- xs, x `elem` ys] == xs\n\n-- 2\u00aa soluci\u00f3n\nsubconjunto2 :: Ord a => [a] -> [a] -> Bool\nsubconjunto2 []     _  = True\nsubconjunto2 (x:xs) ys = x `elem` ys && subconjunto2 xs ys\n\n-- 3\u00aa soluci\u00f3n\nsubconjunto3 :: Ord a => [a] -> [a] -> Bool\nsubconjunto3 xs ys =\n  all (`elem` ys) xs\n\n-- 4\u00aa soluci\u00f3n\nsubconjunto4 :: Ord a => [a] -> [a] -> Bool\nsubconjunto4 xs ys =\n  fromList xs `isSubsetOf` fromList ys\n\n-- Comprobaci\u00f3n de equivalencia\n-- ============================\n\n-- La propiedad es\nprop_subconjunto :: [Int] -> [Int] -> Bool\nprop_subconjunto xs ys =\n  all (== subconjunto1 xs ys)\n      [subconjunto2 xs ys,\n       subconjunto3 xs ys,\n       subconjunto4 xs ys]\n\n-- La comprobaci\u00f3n es\n--    \u03bb> quickCheck prop_subconjunto\n--    +++ OK, passed 100 tests.\n\n-- Comparaci\u00f3n de eficiencia\n-- =========================\n\n-- La comparaci\u00f3n es\n--    \u03bb> subconjunto1 [1..2*10^4] [1..2*10^4]\n--    True\n--    (1.81 secs, 5,992,448 bytes)\n--    \u03bb> subconjunto2 [1..2*10^4] [1..2*10^4]\n--    True\n--    (1.83 secs, 6,952,200 bytes)\n--    \u03bb> subconjunto3 [1..2*10^4] [1..2*10^4]\n--    True\n--    (1.75 secs, 4,712,304 bytes)\n--    \u03bb> subconjunto4 [1..2*10^4] [1..2*10^4]\n--    True\n--    (0.04 secs, 6,312,056 bytes)\n<\/pre>\n<p>El c\u00f3digo se encuentra en <a href=\"https:\/\/github.com\/jaalonso\/Exercitium\/blob\/main\/src\/Reconocimiento_de_subconjunto.hs\">GitHub<\/a>.<\/p>\n<p><b>Soluciones en Python<\/b><\/p>\n<pre lang=\"python\">\nfrom typing import TypeVar\nfrom timeit import Timer, default_timer\nfrom sys import setrecursionlimit\nfrom hypothesis import given, strategies as st\n\nsetrecursionlimit(10**6)\n\nA = TypeVar('A')\n\n# 1\u00aa soluci\u00f3n\ndef subconjunto1(xs: list[A],\n                 ys: list[A]) -> bool:\n    return [x for x in xs if x in ys] == xs\n\n# 2\u00aa soluci\u00f3n\ndef subconjunto2(xs: list[A],\n                 ys: list[A]) -> bool:\n    if xs:\n        return xs[0] in ys and subconjunto2(xs[1:], ys)\n    return True\n\n# 3\u00aa soluci\u00f3n\ndef subconjunto3(xs: list[A],\n                 ys: list[A]) -> bool:\n    return all(x in ys for x in xs)\n\n# 4\u00aa soluci\u00f3n\ndef subconjunto4(xs: list[A],\n                 ys: list[A]) -> bool:\n    return set(xs) <= set(ys)\n\n# Comprobaci\u00f3n de equivalencia\n# ============================\n\n# La propiedad es\n@given(st.lists(st.integers()),\n       st.lists(st.integers()))\ndef test_subconjunto(xs, ys):\n    assert subconjunto1(xs, ys)\\\n           == subconjunto2(xs, ys)\\\n           == subconjunto3(xs, ys)\\\n           == subconjunto4(xs, ys)\n\n# La comprobaci\u00f3n es\n#    src> poetry run pytest -q reconocimiento_de_subconjunto.py\n#    1 passed in 0.34s\n\n# Comparaci\u00f3n de eficiencia\n# =========================\n\ndef tiempo(e):\n    \"\"\"Tiempo (en segundos) de evaluar la expresi\u00f3n e.\"\"\"\n    t = Timer(e, \"\", default_timer, globals()).timeit(1)\n    print(f\"{t:0.2f} segundos\")\n\n# La comparaci\u00f3n es\n#    >>> xs = list(range(20000))\n#    >>> tiempo('subconjunto1(xs, xs)')\n#    1.27 segundos\n#    >>> tiempo('subconjunto2(xs, xs)')\n#    1.84 segundos\n#    >>> tiempo('subconjunto3(xs, xs)')\n#    1.19 segundos\n#    >>> tiempo('subconjunto4(xs, xs)')\n#    0.01 segundos\n<\/pre>\n<p>El c\u00f3digo se encuentra en <a href=\"https:\/\/github.com\/jaalonso\/Exercitium-Python\/blob\/main\/src\/reconocimiento_de_subconjunto.py\">GitHub<\/a>.<\/p>\n<p><b>Comentarios<\/b><\/p>\n<ul>\n<li>La expresi\u00f3n &#8220;x pertenece a ys&#8221; se escribe\n<ul>\n<li>en Haskell, como x &#96;elem&#96; ys<\/li>\n<li>en Python, como x in ys<\/li>\n<\/ul>\n<\/li>\n<li>La expresi\u00f3n &#8220;todos los elementos de xs verifican la propiedad p&#8221; se escribe\n<ul>\n<li>en Haskell, como all p xs<\/li>\n<li>en Python, como all(p(x) for x in xs)<\/li>\n<\/ul>\n<\/li>\n<li>Si xs e ys son conjuntos, la expresi\u00f3n &#8220;xs es subconjunto de ys&#8221; se escribe\n<ul>\n<li>en Haskell, como xs &#96;isSubsetOf&#96; ys<\/li>\n<li>en Python, como xs &lt;= ys<\/li>\n<\/ul>\n<\/li>\n<\/ul>\n","protected":false},"excerpt":{"rendered":"<p>Esta semana he publicado en Exercitium las soluciones de los siguientes problemas: 1. Ra\u00edces de la ecuaci\u00f3n de segundo grado 2. F\u00f3rmula de Her\u00f3n para el \u00e1rea de un tri\u00e1ngulo 3. Intersecci\u00f3n de intervalos cerrados 4. N\u00fameros racionales 5. Reconocimiento de subconjunto A continuaci\u00f3n se muestran las soluciones.<\/p>\n","protected":false},"author":2,"featured_media":0,"comment_status":"closed","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"jetpack_post_was_ever_published":false,"_kad_post_transparent":"","_kad_post_title":"","_kad_post_layout":"","_kad_post_sidebar_id":"","_kad_post_content_style":"","_kad_post_vertical_padding":"","_kad_post_feature":"","_kad_post_feature_position":"","_kad_post_header":false,"_kad_post_footer":false,"_jetpack_newsletter_access":"","_jetpack_dont_email_post_to_subs":false,"_jetpack_newsletter_tier_id":0,"_jetpack_memberships_contains_paywalled_content":false,"footnotes":"","_jetpack_memberships_contains_paid_content":false},"categories":[337],"tags":[],"jetpack_featured_media_url":"","jetpack_sharing_enabled":true,"jetpack_likes_enabled":false,"_links":{"self":[{"href":"https:\/\/www.glc.us.es\/~jalonso\/vestigium\/wp-json\/wp\/v2\/posts\/7794"}],"collection":[{"href":"https:\/\/www.glc.us.es\/~jalonso\/vestigium\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.glc.us.es\/~jalonso\/vestigium\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.glc.us.es\/~jalonso\/vestigium\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/www.glc.us.es\/~jalonso\/vestigium\/wp-json\/wp\/v2\/comments?post=7794"}],"version-history":[{"count":2,"href":"https:\/\/www.glc.us.es\/~jalonso\/vestigium\/wp-json\/wp\/v2\/posts\/7794\/revisions"}],"predecessor-version":[{"id":7796,"href":"https:\/\/www.glc.us.es\/~jalonso\/vestigium\/wp-json\/wp\/v2\/posts\/7794\/revisions\/7796"}],"wp:attachment":[{"href":"https:\/\/www.glc.us.es\/~jalonso\/vestigium\/wp-json\/wp\/v2\/media?parent=7794"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.glc.us.es\/~jalonso\/vestigium\/wp-json\/wp\/v2\/categories?post=7794"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.glc.us.es\/~jalonso\/vestigium\/wp-json\/wp\/v2\/tags?post=7794"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}