Menu Close

Comportamiento del último dígito en primos consecutivos

El pasado 11 de marzo se ha publicado el artículo Unexpected biases in the distribution of consecutive primes en el que muestra que los números primos repelen a otros primos que terminan en el mismo dígito.

La lista de los últimos dígitos de los 30 primeros números es

   [2,3,5,7,1,3,7,9,3,9,1,7,1,3,7,3,9,1,7,1,3,9,3,9,7,1,3,7,9,3]

Se observa que hay 6 números que su último dígito es un 1 y de sus consecutivos 4 terminan en 3 y 2 terminan en 7.

Definir la función

   distribucionUltimos :: Int -> M.Matrix Integer

tal que (distribucionUltimos n) es la matriz cuyo elemento (i,j) indica cuántos de los n primeros números primos terminan en i y su siguiente número primo termina en j. Por ejemplo,

   λ> distribucionUltimos 30
   ( 0 0 4 0 0 0 2 0 0 )
   ( 0 0 1 0 0 0 0 0 0 )
   ( 0 0 0 0 1 0 4 0 4 )
   ( 0 0 0 0 0 0 0 0 0 )
   ( 0 0 0 0 0 0 1 0 0 )
   ( 0 0 0 0 0 0 0 0 0 )
   ( 4 0 1 0 0 0 0 0 2 )
   ( 0 0 0 0 0 0 0 0 0 )
   ( 2 0 3 0 0 0 1 0 0 )
 
   λ> distribucionUltimos (10^5)
   ( 4104    0 7961    0    0    0 8297    0 4605 )
   (    0    0    1    0    0    0    0    0    0 )
   ( 5596    0 3604    0    1    0 7419    0 8387 )
   (    0    0    0    0    0    0    0    0    0 )
   (    0    0    0    0    0    0    1    0    0 )
   (    0    0    0    0    0    0    0    0    0 )
   ( 6438    0 6928    0    0    0 3627    0 8022 )
   (    0    0    0    0    0    0    0    0    0 )
   ( 8830    0 6513    0    0    0 5671    0 3995 )

Nota: Se observa cómo se “repelen” ya que en las filas del 1, 3, 7 y 9 el menor elemento es el de la diagonal.

Soluciones

import Data.Numbers.Primes
import Data.Array
import qualified Data.Matrix as M
 
-- (ultimo n) es el último dígito de n.    
ultimo :: Integer -> Integer
ultimo n = n `mod` 10
 
-- ultimos es la lista de el último dígito de los primos.
--    λ> take 20 ultimos
--    [2,3,5,7,1,3,7,9,3,9,1,7,1,3,7,3,9,1,7,1]
ultimos :: [Integer]
ultimos = map ultimo primes
 
-- ultimosConsecutivos es la lista de los últimos dígitos de los primos
-- consecutivos. 
--    λ> take 10 ultimosConsecutivos
--    [(2,3),(3,5),(5,7),(7,1),(1,3),(3,7),(7,9),(9,3),(3,9),(9,1)]
ultimosConsecutivos :: [(Integer,Integer)]
ultimosConsecutivos = zip ultimos (tail ultimos)
 
-- (histograma r is) es el vector formado contando cuantas veces
-- aparecen los elementos del rango r en la lista de índices is. Por
-- ejemplo, 
--    ghci> histograma (0,5) [3,1,4,1,5,4,2,7]
--    array (0,5) [(0,0),(1,2),(2,1),(3,1),(4,2),(5,1)]
histograma :: (Ix a, Num b) => (a,a) -> [a] -> Array a b
histograma r is = 
    accumArray (+) 0 r [(i,1) | i <- is, inRange r i]
 
distribucionUltimos :: Int -> M.Matrix Integer
distribucionUltimos n =
    M.fromList 9 9 (elems (histograma ((1,1),(9,9)) (take n ultimosConsecutivos)))

Solución en Maxima

distribucionUltimos (n) := block (
  [r : zeromatrix (9,9),
   xs : ultimos (n),
   i, j],
  unless length (xs) < 2 do
    ( i : first (xs),
      j : second (xs),
      r[i,j] : 1 + r[i,j],
      xs : rest (xs)),
  r)$
 
/* ultimos(n) es la lista del último dígito de los n primeros primos.
      (%i5) ultimos (30);
      (%o5) [2,3,5,7,1,3,7,9,3,9,1,7,1,3,7,3,9,1,7,1,3,9,3,9,7,1,3,7,9,3,7]
*/
ultimos (n) := block ([r:[], p:2],
  for k from 0 thru n do
    ( r : cons (mod (p,10), r),
      p : next_prime (p) ),
  reverse (r))$

7 soluciones de “Comportamiento del último dígito en primos consecutivos

  1. fracruzam
    import Data.Array
    import qualified Data.Matrix as M
    import Data.Numbers.Primes
     
    distribucionUltimos :: Int -> M.Matrix Integer
    distribucionUltimos n = M.fromList 9 9 $ map snd $ assocs $ 
       accumArray (+) 0 ((1,1),(9,9)) (take n primos)
      where primos :: [((Int,Int),Integer)]
            primos = zipWith ( x y -> ((x,y),1)) ys xs
              where ys @ (_:xs) = map ultDig primes
            ultDig :: Int -> Int
            ultDig n = n `mod` 10
  2. juamorrom1
    import Data.Numbers.Primes
    import Data.Matrix
     
    distribucionUltimos :: Int -> Matrix Integer
    distribucionUltimos n = matrix 9 9 ((i,j) -> fromIntegral (cuantosCumplen i j n))
     
    cuantosCumplen :: Int -> Int -> Int -> Int
    cuantosCumplen i j n = aux i j (take (n+1) ultimoDigitoPrimos)
                  where aux :: Int -> Int -> [Int] -> Int
                        aux _ _ (y:[]) = 0
                        aux i j (x:y:xs) | x == i && y == j = 1 + aux i j
                                                                 (y:xs)
                                         | otherwise = aux i j (y:xs)
     
    ultimoDigitoPrimos :: [Int]
    ultimoDigitoPrimos = [ last (digitos n) | n <- primes ]
     
    digitos :: Int -> [Int]
    digitos n = [ read [c] | c <- show n ]
     
    -- λ> distribucionUltimos (10^5)
    -- ( 4104    0 7961    0    0    0 8297    0 4605 )
    -- (    0    0    1    0    0    0    0    0    0 )
    -- ( 5596    0 3604    0    1    0 7419    0 8387 )
    -- (    0    0    0    0    0    0    0    0    0 )
    -- (    0    0    0    0    0    0    1    0    0 )
    -- (    0    0    0    0    0    0    0    0    0 )
    -- ( 6438    0 6928    0    0    0 3627    0 8022 )
    -- (    0    0    0    0    0    0    0    0    0 )
    -- ( 8830    0 6513    0    0    0 5671    0 3995 )
     
    -- (6.58 secs, 4,169,524,472 bytes)
  3. josejuan
    import Data.List (tails)
    import Data.Numbers.Primes (primes)
    import qualified Data.Matrix as M
    import qualified Data.IntMap.Strict as I
     
    distribucionUltimos :: Int → M.Matrix Int
    distribucionUltimos n = M.matrix 9 9 g
      where i (a, b) = 10 × a + b
            g k = I.findWithDefault 0 (i k) im
            im  = I.fromListWith (+) [(i (a, b), 1) | (a:b:_) ← tails $ take n $ (`mod` 10) ↥ primes]
     
    {-
    > distribucionUltimos (10^5)
    ( 4104    0 7961    0    0    0 8297    0 4605 )
    (    0    0    1    0    0    0    0    0    0 )
    ( 5596    0 3604    0    1    0 7419    0 8387 )
    (    0    0    0    0    0    0    0    0    0 )
    (    0    0    0    0    0    0    1    0    0 )
    (    0    0    0    0    0    0    0    0    0 )
    ( 6438    0 6928    0    0    0 3627    0 8022 )
    (    0    0    0    0    0    0    0    0    0 )
    ( 8829    0 6513    0    0    0 5671    0 3995 )
     
    (0.63 secs, 541,022,752 bytes)
    -}
  4. alvalvdom1
    import Data.Matrix as M
    import Data.Numbers.Primes
    import Data.List
     
    listaPrimos :: Int -> [Int]
    listaPrimos n = [mod x 10 | x <- take (n+1) primes]
     
    distribucionUltimos :: Int -> M.Matrix Integer
    distribucionUltimos n = M.matrix 9 9 ((i,j) -> genericLength $ filter (==(i,j)) (zip d (tail d)))
                           where d = listaPrimos n
  5. erisan
    import Data.Numbers.Primes
    import Data.Matrix
     
    distribucionUltimos :: Int -> Matrix Integer
    distribucionUltimos n = matrix 9 9 ((i,j) -> fromIntegral (cuantosCumplen i j n))
     
    cuantosCumplen :: Int -> Int -> Int -> Int
    cuantosCumplen i j n = aux i j (take (n+1) ultimoDigitoPrimos)
                  where aux :: Int -> Int -> [Int] -> Int
                        aux _ _ (y:[]) = 0
                        aux i j (x:y:xs) | i == 2 && j == 3 = 1
                                         | even i || even j = 0
                                         | x == i && y == j = 1 + aux i j
                                                                 (y:xs)
                                         | otherwise = aux i j (y:xs)
     
    ultimoDigitoPrimos ::  [Int]
    ultimoDigitoPrimos = [ n `mod` 10 | n <- primes]
     
    {-
    λ> distribucionUltimos (10^5)
    ( 4104    0 7961    0    0    0 8297    0 4605 )
    (    0    0    1    0    0    0    0    0    0 )
    ( 5596    0 3604    0    1    0 7419    0 8387 )
    (    0    0    0    0    0    0    0    0    0 )
    (    0    0    0    0    0    0    1    0    0 )
    (    0    0    0    0    0    0    0    0    0 )
    ( 6438    0 6928    0    0    0 3627    0 8022 )
    (    0    0    0    0    0    0    0    0    0 )
    ( 8830    0 6513    0    0    0 5671    0 3995 )
     
    (4.44 secs, 2,858,694,808 bytes)
    -}
  6. abrdelrod

    Definición en Maxima

    p (i,j,n) := mod (n,10) = i and mod (next_prime (n),10) = j$
     
    aux (n,a) :=
      if n = 0
      then []
      else cons (a,aux (n-1,next_prime (a)))$
     
    nPrimos (n) := aux (n,2)$
     
    f (n,i,j) :=
      length (sublist (create_list (p (i,j,m), m, nPrimos (n)),
                       lambda ([x], x = true)))$
     
    distribucionUltimos(n) :=
      genmatrix (lambda ([i,j],f (n,i,j)),9,9)$

Escribe tu solución

Este sitio usa Akismet para reducir el spam. Aprende cómo se procesan los datos de tus comentarios.