Il numero può raggiungere 1 sottraendo ripetutamente il primo più grande meno di esso?


27

Sfida:

Dato un numero, prendi il primo più grande rigorosamente meno di esso, sottralo da questo numero, fallo di nuovo a questo nuovo numero con il primo più grande di meno e continua a farlo fino a quando è inferiore a 3. Se raggiunge 1, il tuo il programma dovrebbe generare un valore di verità, altrimenti il ​​programma dovrebbe generare un valore di falsa.

Esempi:

Tutti questi dovrebbero dare un valore sincero:

3
4
6
8
10
11
12
14
16
17
18
20
22
23
24
26
27
29
30
32
34
35
37
38
40
41
42
44
46
47
48
50

Tutti questi dovrebbero dare valori falsi:

5
7
9
13
15
19
21
25
28
31
33
36
39
43
45
49

Regole:



1
5-3 = 2, 2 - (- 2) = 4, 4-3 = 1. (/ wiseguy)

@Hurkyl -2 = -1 × 2, quindi non è un numero primo ;-)
ETHproductions

1
@ETHProductions: Ah, ma -1 è un'unità; che la fattorizzazione non contraddice la primalità di -2 non più di 2 = (- 1) × (-2) fa di 2. (o anche 2 = 1 × 2)

3
@ETHproductions: i numeri razionali sono interessanti perché ci sono due approcci molto diversi che sono utili nella pratica! I numeri razionali non hanno numeri primi (nemmeno 2!) Perché tutto è un'unità. Tuttavia, puoi anche visualizzare i razionali come una costruzione fatta dagli interi e studiarli usando i numeri primi degli interi. (es. chiunque chieda la scomposizione in 9/102^(-1) 3^2 5^(-1)

Risposte:


8

Gelatina , 9 8 byte

’ÆRṪạµ¡Ḃ

Provalo online! o verifica tutti i casi di test .

Come funziona

’ÆRṪạµ¡Ḃ  Main link. Argument: n

     µ    Combine all atoms to the left into a chain.
’           Decrement; yield n - 1.
 ÆR         Prime range; yield all primes in [2, ..., n -1].
   Ṫ        Tail; yield p, the last prime in the range.
            If the range is empty, this yields p = 0.
    ạ       Compute the absolute difference of p and n.
      ¡   Call the chain to the left n times.
          This suffices since each iteration decreases n, until one of the fixed
          points (1 or 2) is reached.
       Ḃ  Bit; return the parity of the fixed point.

11

Retina , 31 byte

.+
$*
+`1(?!(11+)\1+$)11+
1
^1$

Stampe 0(falsa) o 1(verità).

Provalo online! (La prima riga abilita una suite di test separata da avanzamento riga.)

Spiegazione

.+
$*

Converti input in unario trasformando input Nin Ncopie di 1.

+`1(?!(11+)\1+$)11+
1

Rimuovere ripetutamente il primo più grande meno dell'input. Questo si basa sul test di primalità standard con regex .

^1$

Controlla se il risultato è un singolo 1.


Come è possibile utilizzare Retina senza unario? Oo
Addison Crump,

@Syxer le prime due righe convertono l'input in unario.
Martin Ender,

Ciò non significa che puoi rimuoverli e richiedere un input unario?
Addison Crump,

2
@Syxer ho potuto, ma ho smesso di farlo. Sembra un formato I / O instabile, e ora che la conversione è di 6 byte (al contrario di ~ 200 rispetto a una volta), non penso che Retina conti come "non può ragionevolmente accettare input in decimali".
Martin Ender,

Ah, capisco. Ho mai visto input unari in Retina, quindi la mia confusione.
Addison Crump,

8

Pyth, 18 15 14 byte

Grazie a @Maltysen per -1 byte

#=-QefP_TUQ)q1

Un programma che accetta input su STDIN e stampa Trueo Falsecome appropriato.

Provalo online

Come funziona

#=-QefP_TUQ)q1  Program. Input: Q
#          )    Loop until error statement (which occurs when Q<3):
         UQ      Yield [0, 1, 2, 3, ..., Q-1]
     fP_T        Filter that by primality
    e            Yield the last element of that
 =-Q             Q = Q - that
            q1  Q is 1 (implicit variable fill)
                Implicitly print

Vecchia versione con riduzione, 18 byte

qu-G*<HGH_fP_TSQQ1

Provalo online

Come funziona

qu-G*<HGH_fP_TSQQ1  Program. Input: Q
              SQ    Yield [1, 2, 3, ..., Q]
          fP_T      Filter that by primality
         _          Reverse it
 u                  Reduce it:
                Q    with base case Q and
                     function G, H -> 
     <HG              H<G
    *   H             *H (yields H if H<G, else 0)
  -G                  Subtract that from G
q                1  The result of that is 1
                    Implicitly print

Stè di U15 caratteri
Maltysen l'

7

JavaScript (ES6), 64 63 byte

Salvato 1 byte grazie a @Neil

g=(x,n=x-1)=>n<2?x:x%n?g(x,n-1):g(x-1)
f=x=>x<3?x%2:f(x-g(x-1))

L'ho scritto in 2 minuti ... e ha funzionato perfettamente la prima volta. Il primo utente a trovare l'inevitabile bug vince ....

Provalo

Come funziona

Per prima cosa definiamo g (x) come la funzione che trova il primo numero primo p <= x . Questo viene fatto usando il seguente processo:

  1. Inizia con n = x-1 .
  2. Se n <2 , x è primo; ritorna x .
  3. Se x è divisibile per n , decrementa x e vai al passaggio 1.
  4. Altrimenti, decrementa n e vai al passaggio 2.

La soluzione a questa sfida, f (x) , è ora abbastanza semplice:

  1. Se x <3 , restituisce x = 1 .
  2. Altrimenti, sottrarre g (x-1) e riprovare.

4326, che dovrebbe restituire true non sembra restituire, ma 4328 (true) e 4329 (false) lo fanno, si tratta di una limitazione JS o di un bug?
Jonathan Allan,

@JonathanAllan 4326 viene inviato too much recursionalla console del browser in Firefox 48, quindi immagino che la ricorsione superi il limite di ricorsione di FF.
ETHproductions

Sì, il prossimo primo down è 4297 (e il successivo up è 4327), motivo per cui 4328 funziona.
Jonathan Allan,

4
x%2dovrebbe salvarti un byte x==1.
Neil,

@Neil non ci avrei mai pensato :-)
ETHproductions,

6

Pyke, 15 11 byte

WDU#_P)e-Dt

Provalo qui!

            - stack = input
W           - while continue:
  U#_P)     -     filter(is_prime, range(stack))
       e    -    ^[-1]
 D      -   -   stack-^
         Dt -  continue = ^ != 1

Restituisce 1se vero e genera un'eccezione se falso


5

Julia, 32 byte

Anche se non sarà la soluzione più breve tra le lingue, questa potrebbe essere la più breve di quelle leggibili dall'uomo ...

!n=n>2?!(n-primes(n-1)[end]):n<2

O, per dirla in termini leggermente più chiari

function !(n)
  if n>2
    m=primes(n-1)[end]   # Gets largest prime less than n
    return !(n-m)        # Recurses
  else
    return n<2           # Gives true if n is 1 and false if n is 2
  end
end

Chiamato con, ad esempio !37,.


3

Mathematica, 32 byte

2>(#//.x_/;x>2:>x+NextPrime@-x)&

Questa è una funzione senza nome che accetta un numero intero e restituisce un valore booleano.

Spiegazione

C'è molta sintassi e un ordine di lettura divertente qui, quindi ...

   #                               This is simply the argument of the function.
    //.                            This is the 'ReplaceRepeated' operator, which applies
                                   a substitution until the its left-hand argument stops
                                   changing.
       x_/;x>2                     The substitution pattern. Matches any expression x as
                                   long as that expression is greater than 2.
              :>                   Replace that with...
                  NextPrime@-x     Mathematica has a NextPrime built-in but no
                                   PreviousPrime built-in. Conveniently, NextPrime
                                   works with negative inputs and then gives you the 
                                   next "negative prime" which is basically a
                                   PreviousPrime function (just with an added minus sign).
                x+                 This gets added to x, which subtracts the previous
                                   prime from it.
2>(                           )    Finally, we check whether the result is less than 2.

Battiti ravvicinati #+0~Min~NextPrime@-#&~FixedPoint~#==1&(36 byte). Bel uso di //.!
Greg Martin,

1
@GregMartin 35 quando lo usi <2alla fine.
Martin Ender,

3

Python3, 102 92 90 89 88 byte

f=lambda n:n<2if n<3else f(n-[x for x in range(2,n)if all(x%y for y in range(2,x))][-1])

Suggerimenti di golf benvenuti! Vedo che gmpycontiene una funzione next_prime, ma non riesco ancora a provarla :(

-2 byte, grazie a @JonathanAllan !

-1 byte, grazie a @Aaron !

Casi test

f=lambda n:n<2if n<3else f(n-[x for x in range(2,n)if all(x%y for y in range(2,x))][-1])

s="3 4 6 8 10 11 12 14 16 17 18 20 22"
h="5 7 9 13 15 19 21 25 28 31 33 36 39"

for j in s.split(" "):print(f(int(j)))
for j in h.split(" "):print(f(int(j)))

L'output è 13 valori di verità e 13 valori di falsità. scontiene i casi veritieri e hi falsi.


1
if all(x%y for...funziona
Jonathan Allan l'

1
n<3 else-> n<3elseper ottenere la stessa lunghezza della mia;)
Aaron,

2

Python, con sympy, 60 byte

import sympy
f=lambda n:n>2and f(n-sympy.prevprime(n))or n<2

Il mio metodo precedente era 83 byte senza sympy usando la ricorsione, ma ho preso verità / falsità per significare distinguibile e coerente, ma sono stato informato che è un'interpretazione errata. Non riesco a salvarlo a causa della coda, ma lo lascerò qui nel caso qualcuno sappia come farlo:

f=lambda n,p=0:n>2and(any(p%x==0for x in range(2,p))and f(n,p-1)or f(n-p,n+~p))or n


@ mbomb007 Ho pensato che le specifiche fossero "vere o false", se necessario, mentre "verità o falsità" significa distinguibile e coerente?
Jonathan Allan,

1
No. Sono definiti come abbiamo deciso sul meta sito. Qualsiasi domanda che consenta un output "distinguibile e coerente" deve specificarlo, piuttosto che verità / falsità.
mbomb007,

OK, ho letto questo , ad un certo punto aggiornerò ...
Jonathan Allan,

1

Vitsy, 28 26 byte

Questo può sicuramente essere abbreviato.

<]xN0)l1)-1[)/3D-];(pD-1[D

<                    Traverse the code in this direction, rotating on the line.
                     For the sake of reading the code easier, I'm reversing the
                     code on this line. This will be the order executed.

 D[1-Dp(;]-D3/)[1-)1l)0Nx]
 D                         Duplicate the top member of the stack.
  [      ]                 Do the stuff in brackets until break is called.
   1-                      Subtract 1 from the top item of the stack.
     D                     Duplicate the top member of the stack.
      p(                   If the top member is a prime...
        ;                  break;
          -                Pop a, b, push a - b.
           D3/)[         ] If this value is less than 3, do the bracketed code.
                1-         Subtract the top item of the stack by 1.
                  )        If the top item is zero...
                   1       Push 1.
                    l)     If the length of the stack is zero...
                      0    Push 0.
                       N   Output the top member of the stack.
                        x  System.exit(0);

Provalo online!


1

MATL , 13 byte

`tqZq0)-t2>}o

Provalo online! Oppure verifica tutti i casi di test contemporaneamente .

Spiegazione

`        % Do...while
  t      %   Duplicate. Takes input implicitly in the first iteration
  qZq    %   All primes less than that
  0)     %   Get last one
  -      %   Subtract (this result will be used in the next iteration, if any)
  t      %   Duplicate
  2>     %   Does it exceed 2? If so: next iteration. Else: execute the "finally" 
         %   block and exit do...while loop
}        % Finally
  o      %   Parity. Transforms 2 into 0 and 1 into 1
         % End do...while implicitly
         % Display implicitly

1

CJam , 21 16 byte

Grazie a Dennis per aver salvato 4 byte.

ri{_1|{mp},W=-}h

Provalo online!

Spiegazione

ri       e# Read input and convert to integer N.
{        e# Run this block as long as N is positive (or until the program aborts
         e# with an error)...
  _1|    e#   Duplicate and OR 1. This rounds up to an odd number. For N > 2, this
         e#   will never affect the greatest prime less than N.
  {mp},  e#   Get all primes from 0 to (N|1)-1.
         e#   For N > 2, this will contain all primes less than N.
         e#   For N = 2, this will contain only 2.
         e#   For N = 1, this will be empty.
  W=     e#   Select the last element (largest prime up to (N|1)-1).
         e#   For N = 1, this will result in an error and terminate the program, which
         e#   still prints the stack contents though (which are 1, the desired output).
  -      e#   Subtract from N. Note that this gives us 0 for N = 2, which terminates the 
         e#   loop.
}h

ri_{_1|{mp},W=-}*dovrebbe funzionare.
Dennis,

@Dennis Grazie, 1|è davvero intelligente. :) (E dimentico sempre che {...},fa un intervallo implicito ...)
Martin Ender l'

1

Perl, 42 byte

Include +1 per -p

Esegui con input su STDIN

reach1.pl:

#!/usr/bin/perl -p
$_=1x$_;$_=$`while/\B(?!(11+)\1+$|$)|11$/

Usa la regex di primalità classica


1

.NET Regex, 38 byte

Solo per dimostrare che può essere verificato in una singola regex.

^(?>(?<=(.*))..+(?<!^\1\2+(.+.)|$))+.$

Si presume che l'input sia in unario.

Spiegazione

Implementa semplicemente il requisito per la parola, rimuovendo ripetutamente il primo più grande e verificando se il resto è 1.

  • (?>(?<=(.*))..+(?<!^\1\2+(.+.)|$))+: Il gruppo senza backtracking si assicura che il primo più grande che abbiamo trovato non sia annullato, e +semplicemente ripete il processo di abbinamento del primo più grande.

    • (?<=(.*))..+(?<!^\1\2+(.+.)|$): Abbina il primo più grande meno del numero rimanente

      • (?<=(.*)): Registra quanto abbiamo sottratto per stabilire un punto di "ancoraggio" per l'affermazione.

      • ..+: Cerca il numero più grande ...

      • (?<!^\1\2+(.+.)|$): ... che è primo e inferiore al numero rimanente.
        • (?<!^\1\2+(.+.)): La solita routine di test primi, con ^\1virata davanti per essere sicuri che stiamo controllando l'importo abbinato..+
        • (?!<$): Asserire meno del numero rimanente

La (?<=(.*))parte è piuttosto goffa. Non sono sicuro se esiste un modo migliore. Inoltre, sono curioso di sapere se esiste una soluzione in PCRE.
n̴̖̋h̷͉̃a̷̭̿h̸̡̅ẗ̵̨́d̷̰̀ĥ̷̳,

0

Perl 6 ,  54 53 52  51 byte

{($_,{$_-($_-1...2).first: *.is-prime}...3>*)[*-1]==1}
{($_,{$_-($_-1...2).first: *.is-prime}...3>*).any==1}
{any($_,{$_-($_-1...2).first: *.is-prime}...3>*)==1}
{any($_,{$_-(^$_).grep(*.is-prime)[*-1]}...3>*)==1}

Spiegazione:

# bare block lambda with implicit parameter 「$_」
# used to generate all of the rest of the elements of the sequence
{
  # create an any Junction of the following list
  any(
    $_, # initialize sequence with the inner block's argument

    # bare block lambda with implicit parameter 「$_」
    {
      # take this inner block's argument and subtract
      $_ -

      ( ^$_ )            # Range up-to and excluding 「$_」
      .grep(*.is-prime)\ # find the primes
      [ * - 1 ]          # return the last value
    }

    ...   # keep doing that until

    3 > * # the result is less than 3

  # test that Junction against 「1」
  # ( returns an 「any」 Junction like 「any(False, False, True)」 )
  ) == 1
}

Esempio:

# show what is returned and if it is truthy
sub show ($_) {
  # 「.&{…}」 uses the block as a method and implicitly against 「$_」
  my $value = .&{any($_,{$_-(^$_).grep(*.is-prime)[*-1]}...3>*)==1}
  say join "\t", $_, ?$value, $value.gist;
}

show 3;  # 3    True    any(False, True)
show 4;  # 4    True    any(False, True)
show 5;  # 5    False   any(False, False)
show 10; # 10   True    any(False, False, True)
show 28; # 28   False   any(False, False, False)
show 49; # 49   False   any(False, False)
show 50; # 50   True    any(False, False, True)

0

Irregolare , 63 byte

p~?1_$-1p:;
n=i(0)?1_$-1p:;
_~
N=n
1(?!(11+)\1+$)11+~1
^11$~0
N

Ho creato questo linguaggio due giorni fa e le premesse di base sono che non esistono loop integrati, le uniche caratteristiche sono l'aritmetica di base e il processo decisionale e la valutazione del programma si basa su espressioni regolari.

Spiegazione

p~?1_$-1p:;
n=i(0)?1_$-1p:;
_~
N=n

Questa parte converte l'input in unario. Sottrae ripetutamente 1 dall'input fino a quando non è uguale a 0, anteponendo 1_ogni volta. Quindi rimuove tutti _i messaggi. Se non avessi dimenticato un breaknel mio codice, potrebbe essere scritto come segue:

p~?1_$-1p:;
_~
n=i(0)?1_$-1p:;

La parte successiva rimuove ripetutamente il primo più grande dall'input fino a quando non è uguale a 1o 11, con la 11sua sostituzione con 0.

1(?!(11+)\1+$)11+~1
^11$~0
N

Ho usato il regex dalla risposta di Martin Ender .


0

Haskell, 79 byte

Non proprio breve ma inutile :)

(<2).until(<3)(until(flip(`until`(+1))2.(.)(<1).mod>>=(==))pred.pred>>=flip(-))

0

PowerShell v2 +, 81 byte

param($n)while($n-gt2){$n-=(($n-1)..2|?{'1'*$_-match'^(?!(..+)\1+$)..'})[0]}!--$n

Accetta input $n. Entra in un whileciclo fintanto che $nè fermo 3o maggiore. Ogni iterazione sottrae un numero da $n. Il numero è il risultato del test di primalità regex applicato su un intervallo ($n-1)..2tramite l' operatore Where-Object( ?), quindi il primo [0]dei risultati (poiché l'intervallo sta diminuendo, si ottiene quello più grande selezionato). Dopo aver concluso il ciclo, $nsarà 1o 2, per definizione, quindi pre-diminuiamo $n(trasformandolo in uno 0o 1), e prendiamo il booleano, non di !esso. Rimane in cantiere e l'output è implicito.

Esempi

PS C:\Tools\Scripts\golfing> 3..20|%{"$_ --> "+(.\can-the-number-reach-one.ps1 $_)}
3 --> True
4 --> True
5 --> False
6 --> True
7 --> False
8 --> True
9 --> False
10 --> True
11 --> True
12 --> True
13 --> False
14 --> True
15 --> False
16 --> True
17 --> True
18 --> True
19 --> False
20 --> True

0

Matlab, 51 byte

v=@(x)x-max(primes(x-1));while(x>=3)x=v(x);end;x==1

Questo è MOLTO simile alla soluzione JS6 di ETHProductions , ma necessita che la variabile sia nell'area di lavoro.


0

Python 2.7: 88 87 byte

r=lambda n:n>2and r(n-[a for a in range(2,n)if all(a%b for b in range(2,a))][-1])or n<2

Thx @TuukkaX per -1 byte in più!


1
Aggiorna la tua descrizione;) Inoltre, potresti salvare un byte dicendo n<2invece di n==1.
Yytsi,


0

Clojure, 125 byte

#(loop[x %](if(> x 2)(recur(- x(loop[y(dec x)](if(some zero?(vec(for[z(range 2 y)](mod y z))))(recur(dec y))y))))(quot 1 x)))

Yikes, questo è un lungo pezzo di codice. Il linguaggio più prolisso colpisce ancora!

Ungolfed:

(defn subprime [n]
  (loop [x n]
    (if (> x 2)
      (recur
        (- x
          (loop [y (dec x)]
            (if (some zero? (vec (for [z (range 2 y)] (mod y z))))
              (recur (dec y)) y))))
      (quot 1 x))))
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.