Calcular os fatores primos


27

Tivemos um grande desafio de fatoração há um tempo atrás, mas esse desafio tem quase seis anos e mal atende aos nossos requisitos atuais, então acredito que está na hora de um novo.

Desafio

Escreva um programa ou função que tome como entrada um número inteiro maior que 1 e produza ou retorne uma lista de seus fatores primos.

Regras

  • A entrada e a saída podem ser fornecidas por qualquer método padrão e em qualquer formato padrão.
  • Fatores duplicados devem ser incluídos na saída.
  • A saída pode estar em qualquer ordem.
  • A entrada não será menor que 2 ou maior que 2 31 - 1.
  • Os internos são permitidos, mas é recomendável incluir uma solução não interna.

Casos de teste

2 -> 2
3 -> 3
4 -> 2, 2
6 -> 2, 3
8 -> 2, 2, 2
12 -> 2, 2, 3
255 -> 3, 5, 17
256 -> 2, 2, 2, 2, 2, 2, 2, 2
1001 -> 7, 11, 13
223092870 -> 2, 3, 5, 7, 11, 13, 17, 19, 23
2147483646 -> 2, 3, 3, 7, 11, 31, 151, 331
2147483647 -> 2147483647

Pontuação

Isso é , então o código mais curto em bytes vence.


2
Teria sido muito melhor se você não permitisse embutidos.
Buffer Over Leia

2
Os desafios @TheBitByte que desautorizam os embutidos geralmente são vistos como desafios Do X sem Y , especialmente porque às vezes é difícil dizer se uma solução é tecnicamente embutida.
ETHproductions

1
Bem, aproveite o influxo de soluções de <5 bytes! Enquanto escrevo isso, o Pyth já faz isso em 1 byte.
Buffer Over Leia

2
@TheBitByte Pense nisso como um desafio idioma por idioma, principalmente. Tente vencer a solução do Python, ou alguma outra linguagem sem um builtin.
Isaacg

1
@isaacg Bem, idioma por idioma é uma maneira melhor de encarar isso, eu concordo.
Buffer Over Leia

Respostas:




10

Python 2, 53 bytes

f=lambda n,i=2:n/i*[f]and[f(n,i+1),[i]+f(n/i)][n%i<1]

Tenta cada divisor iem potencial por vez. Se ié um divisor, o anexa e reinicia com n/i. Senão, tenta o próximo divisor mais alto. Como os divisores são verificados em ordem crescente, apenas os primos são encontrados.

Como um programa, para 55 bytes:

n=input();i=2
while~-n:
 if n%i:i+=1
 else:n/=i;print i

8

Mathematica, 38 30 bytes

Obrigado @MartinEnder por 8 bytes!

Join@@Table@@@FactorInteger@#&

Que tal FactorInteger[#][[All, 1]]&? 26 bytes
David G. Stork

@ DavidG.Stork que não iria funcionar porque não iria repetir os fatores primos se o poder é maior que 1.
JungHwan Min



4

JavaScript (ES6), 44 bytes

f=(n,x=2)=>n-1?n%x?f(n,x+1):[x,...f(n/x)]:[]

Horrivelmente ineficiente devido ao fato de iterar de 2 a todos os fatores primos, incluindo o último. Você pode reduzir drasticamente a complexidade do tempo ao custo de 5 bytes:

f=(n,x=2)=>x*x>n?[n]:n%x?f(n,x+1):[x,...f(n/x,x)]


3

Na verdade , 6 bytes

w`in`M

Experimente online!

Explicação:

w`in`M
w       factor into primes and exponents
 `in`M  repeat each prime # of times equal to exponent

Você provavelmente pode apenas usar oagora, certo?
Oliver

@ Oliver Sim, mas normalmente não atualizo respostas antigas com os builtins.
Mego 21/06

3

J, 2 bytes

q:

O corpo deve ter pelo menos 30 caracteres.




2

surdo , 3 bytes

Essa linguagem é bastante jovem e ainda não está pronta para qualquer coisa importante, mas pode ser fatorada como primordial:

A/D

Isso aguardará a entrada do usuário e emitirá a lista de fatores primos.


2

MATLAB, 6 bytes

Eu acho que isso não requer nenhuma explicação.

factor

1

Bash + coreutils, 19 bytes

factor|sed s/.*:.//

Experimente online!


Você pode cortar um byte se o espaço em branco não importar na saída usando factor|sed s/.*://. Também factor|cut -d: -f2(ou factor|cut -d\ -f2para corresponder à sua saída atual) é o mesmo comprimento de bytes, mas será executado mais rapidamente e usará menos sobrecarga de memória.
Caleb

Vou perguntar ao OP sobre espaço em branco. Infelizmente, eu precisaria factor|cut -d\ -f2-eliminar o espaço inicial, que é um byte mais longo.
Dennis

1

Lote, 96 bytes

@set/an=%1,f=2,r=0
:l
@set/af+=!!r,r=n%%f
@if %r%==0 echo %f%&set/an/=f
@if %n% gtr 1 goto l


1

Hexagonia , 58 bytes

Ainda não terminou o golfe, mas o @MartinEnder deve ser capaz de destruir isso de qualquer maneira

Imprime fatores separados por espaço, com um espaço à direita

Golfe:

2}\..}$?i6;>(<...=.\'/})."@...>%<..'':\}$"!>~\{=\)=\}&<.\\

Estabelecido:

     2 } \ . .
    } $ ? i 6 ;
   > ( < . . . =
  . \ ' / } ) . "
 @ . . . > % < . .
  ' ' : \ } $ " !
   > ~ \ { = \ )
    = \ } & < .
     \ \ . . .

Explicação em breve.




1

C, 92 bytes

int p(int n){for(int i=2;i<n;i++)if(n%i==0)return printf("%d, ",i)+p(n/i);printf("%d\n",n);}

Versão não destruída:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>

int prime(int number) {
    for (int i = 2; i < number; i++) {
        if (number % i == 0) {
            printf("%d, ", i);
            return prime(number / i); //you can golf away a few bytes by returning the sum of your recursive function and the return of printf, which is an int
        }                             //this allow you to golf a few more bytes thanks to inline calls
    }
    printf("%d\n", number);
}

int main(int argc, char **argv) {
    prime(atoi(argv[1]));
}




0

Perl 6 , 77 64 bytes  

{my$a=$_;.is-prime??$_!!map ->\f{|({$a%f||($a/=f)&&f}...^*!= f)},(2... *>$a)}

Tente

{my$a=$_;map ->\f{|({$a%f||($a div=f)&&f}...^ f>*)},(2... *>$a)}

Experimente (Nota: não tem tempo suficiente para terminar)


Uma versão com muito mais desempenho é um pouco mais longa, com 100 bytes.

{my$a=$_;map ->\f{|({$a.is-prime??($/=$a)&&($a=0)||$/!!($a%f||($a div=f)&&f)}...^ f>*)},(2... *>$a)}

Tente


Expandido: (versão de 64 bytes)

{
  my $a = $_;  # the input 「$_」 is read-only by default
  map
    -> \f {
      |(              # slip ( flattens into outer list )

        # generate sequence of 0 or more 「f」s
        {
          $a % f      # is it not evenly divisible

          ||          # if it is evenly divisible
          ($a div=f)  # divide it
          &&          # and
          f           # return 「f」
        }
        ...^   # keep doing that until
        f > *  # 「f」 is bigger
      )

    },

    # do that over the following list

    (2 ... * > $a) # generate a sequence from 2
                   # up to whatever the value of $a
                   # is at the time of the check
}

0

VB.NET, 86 bytes

Teve isso em torno de alguns programas do Project Euler. Removidas as otimizações no interesse da falta, e este é o resultado. Naturalmente, o VB é muito detalhado, por isso é bastante longo. Não estou contando os principais espaços em branco. Pode ser omitido, mas é mais fácil ler com ele.

Isso leva um número inteiro como parâmetro e imprime os fatores primos com uma vírgula depois. Há uma vírgula no final.

Sub A(a)
    For i=2To a ' VB re-evaluates a each time, so the /= at the end of the loop shortens this
        While a Mod i=0 ' this is a factor. We've grabbed primes before this, so this must be a prime factor
            Console.Write(i &",") ' output
            a/=i ' "mark" the prime as "used"
        End While
    Next
End Sub

0

Perl 6 , 51 bytes

Uma solução recursiva:

sub f(\n,\d=2){n-1??n%d??f n,d+1!!(d,|f n/d,d)!!()}

0

Java (OpenJDK) , 259 bytes

import java.util.*;interface g{static void main(String[]z){int a=new Scanner(System.in).nextInt();int b=0;int[]l={};for(int i=2;i<=a;i++){for(;a%i<1;l[b-1]=i){l=Arrays.copyOf(l,b=l.length+1);a/=i;}}for(int i=0;i<b;i++)System.out.print(l[i]+(i<b-1?", ":""));}}

Experimente online!


Consulte esta lista para ver como esse envio pode ser aprimorado: gist.github.com/kritixilithos/fde37dc5a8ae54852aa134a6e70ea495 . Se você precisa esclarecer alguma coisa, fique à vontade para me executar ping no byte 19 :)
Kritixi Lithos

0

Ruby, 61 bytes

require'prime';->x{x.prime_division.flat_map{|x|[x[0]]*x[1]}}

Versão mais curta que eu consegui pensar.


Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.