Quanti modi per scrivere N come prodotto di numeri interi M?


12

Dato un numero intero N , conta quanti modi in cui può essere espresso come prodotto di numeri interi M > 1.

L'input è semplicemente N e M e l'output è il conteggio totale di gruppi interi distinti . Significa che puoi usare un numero intero più di una volta, ma ogni gruppo deve essere distinto ( 3 x 2 x 2non conterebbe se 2 x 2 x 3è presente).

vincoli

1 < N <2 31
1 < M <30

Esempi

L'input 30 2fornisce output 3, poiché può essere espresso in 3 modi:

2 x 15
3 x 10
5 x 6

L'input 16 3fornisce output 1, poiché esiste un solo gruppo distinto:

2 x 2 x 4

L'input 2310 4fornisce output 10:

5 x 6 x 7 x 11
3 x 7 x 10 x 11
3 x 5 x 11 x 14
3 x 5 x 7 x 22
2 x 7 x 11 x 15
2 x 5 x 11 x 21
2 x 5 x 7 x 33
2 x 3 x 11 x 35
2 x 3 x 7 x 55
2 x 3 x 5 x 77

L'input 15 4fornisce output 0, poiché non può essere eseguito.

Regole

Si applicano scappatoie da golf con codice standard, insieme a definizioni standard per input / output. Le risposte possono essere una funzione o un programma completo. Le funzioni integrate per la fattorizzazione e / o il partizionamento non sono consentite, ma altre vanno bene. Il codice viene conteggiato in byte.


Cosa intendi per partizionamento?
Ottimizzatore il

@Optimizer Raggruppamento di un elenco in elenchi secondari non sovrapposti. Alcune lingue lo hanno incorporato, come Mathematica .
Geobits il

C'è un limite di tempo? Un algoritmo particolarmente ingenuo potrebbe richiedere secoli per un grande valore di M. Cose semplici come notare che può esserci solo un fattore più grande di sqrt (N) ovviamente aiuta molto.
Level River St,

1
@steveverrill Dato il limite superiore su N , dovrebbero esserci solo 30 (primi) fattori al massimo, che velocizzano un po 'le cose. Tuttavia, sentiti libero di essere ingenuo. Se è probabile che il tuo algoritmo non fornisca una risposta entro poche ore, una prova del concetto ben spiegata potrebbe aiutare gli elettori a decidere.
Geobits il

è consentito un prodotto incorporato che consente di realizzare prodotti cartesiani di due elenchi?
Ottimizzatore il

Risposte:


5

Pyth - 24 23 22 21 byte

Non è una soluzione complicata. Giocherà a golf di più. Prende solo il prodotto cartesiano di elenchi e filtri. Stessa strategia di @optimizer (sto indovinando a causa del suo commento, in realtà non ha decifrato quel CJam) Grazie a @FryAmTheEggman per 2 byte e ingannando con M.

Ml{m`Sdfqu*GHT1G^r2GH

Definisce una funzione gcon args GeH

M                    function definition of g with args G and H
 l                   length of
  {                  set (eliminates duplicates)
   m                 map
    `Sd              repr of sorted factors so can run set (on bash escape ` as \`)
    f                filter
     q      G        equals first arg
      u*GHT1         reduce by multiplication
     ^     H         cartesian product by repeat second arg
       r2G           range 2 to first arg

Ha funzionato su tutti gli argomenti di test tranne l'ultimo, è stato troppo lento su quello, ma non vi è alcun limite di tempo.


L'input va bene in quel formato.
Geobits il

1
Pyth golf tip: se ottieni 2 argomenti, di solito è più breve da usare Mche definisce la funzione gdi 2 argomenti Ge H. Questo è ciò che ho per questo: Ml{msdfqu*GHT1G^r2GH. Sempre bello vedere un altro utente
Pyth

@FryAmTheEggman aggiornato grazie per il suggerimento.
Maltysen,

1
Questo sembra dare una risposta errata per l'input 72 3, che restituisce 5, ma in realtà ci sono 6 risposte,(2, 2, 18), (2, 3, 12), (2, 4, 9), (2, 6, 6), (3, 3, 8)
isaacg

1
@isaacg oh ok, tornerò alla mia versione da 21 caratteri. Non pensavo che sommarlo avrebbe funzionato, ma sembrava, quindi torno a ripr. Grazie per la cattura.
Maltysen,

9

Python 3, 59

f=lambda N,M,i=2:i<=N and f(N/i,M-1,i)+f(N,M,i+1)or-~M==N<2

Contiamo potenziali divisori i. Con l'argomento aggiuntivo icome divisore più basso consentito, la relazione ricorsiva di base è

f(N,M,i)=f(N/i,M-1,i)+f(N,M,i+1)

Per ognuno i, scegliamo di includerlo (possibile come ripetizione), nel qual caso dividiamo il prodotto richiesto Nper ie diminuiamo M. Se non lo facciamo, aumentiamo idi 1, ma solo se i<N, dal momento che è inutile controllare i divisori maggiori di N.

Quando il divisore minimo isupera N, non ci sono più potenziali divisori. Quindi, controlliamo se siamo riusciti vedendo se M==0 and N==1, o, in modo equivalente, M+1==N==1o M+1==N<2, da quando M+1==N, il valore reciproco è garantito per essere un numero intero positivo (grazie a FryAmTheEggman per questa ottimizzazione).

Questo codice causerà un overflow dello stack per Ncirca 1000 sulla maggior parte dei sistemi, ma è possibile eseguirlo in Stackless Python per evitarlo. Inoltre, è estremamente lento a causa della sua ramificazione esponenziale ricorsiva.


Penso che tu possa usare-~M==N<2
FryAmTheEggman il

@FryAmTheEggman Ho pensato che avrebbe dato falsi positivi, ma in effetti funziona, grazie ai vincoli comuni su Me N. Grazie!
xnor

4

Ruby, 67

f=->n,m,s=2,r=0{m<2?1:s.upto(n**0.5){|d|n%d<1&&r+=f[n/d,m-1,d]}&&r}

In realtà ragionevolmente efficiente per una definizione ricorsiva. Per ogni coppia divisore [d,q]di n, dessendo il più piccolo, sommiamo il risultato di f[q,m-1]. La parte difficile è che nelle chiamate interne, limitiamo i fattori a quelli maggiori o uguali a d in modo da non finire con il doppio conteggio.

1.9.3-p327 :002 > f[30,2]
 => 3 
1.9.3-p327 :003 > f[2310,4]
 => 10 
1.9.3-p327 :004 > f[15,4]
 => 0 
1.9.3-p327 :005 > f[9,2]
 => 1 

2

CJam, 48 byte

Questo può essere molto più breve ma ho aggiunto alcuni controlli per farlo funzionare per un numero decente di Msul compilatore online.

q~\:N),2>{N\%!},a*{_,2/)<m*{(+$}%}*{1a+:*N=},_&,

Provalo online qui


Questo è un bug. Prova a inserire 2 1. Uscita prevista: 1. Uscita effettiva: 0.
Peter Taylor,

@PeterTaylor Sigh. Fisso.
Ottimizzatore

2

T-SQL 456 373

Sono sicuro che questo si interromperà quando gli input sono quasi vicini all'ampiezza.

Grazie a @MickyT per aver contribuito a salvare molti personaggi con CONCAT e SELEZIONE anziché più SET.

CREATE PROC Q(@N INT,@M INT)AS
DECLARE @ INT=2,@C VARCHAR(MAX)='SELECT COUNT(*)FROM # A1',@D VARCHAR(MAX)=' WHERE A1.A',@E VARCHAR(MAX)=''CREATE TABLE #(A INT)WHILE @<@N
BEGIN
INSERT INTO # VALUES(@)SET @+=1
END
SET @=1
WHILE @<@M
BEGIN
SELECT @+=1,@C+=CONCAT(',# A',@),@D+=CONCAT('*A',@,'.A'),@E+=CONCAT(' AND A',@-1,'.A<=A',@,'.A')END
SET @C+=CONCAT(@D,'=',@N,@E)EXEC(@C)

Vorrei votare questo, ma non riesco a trovare un modo semplice per testarlo. Qualche idea? Anche la conferma da parte di terzi del corretto funzionamento.
Geobits il

Ottengo un paio di errori di conversione quando lo eseguo (2012). Sembrano provenire da queste dichiarazioni SET @C+=',# A'+@eSET @D+='*A'+@+'.A'SET @E+=' AND A'+(@-1)+'.A<=A'+@+'.A'
MickyT

Dovrai anche risolvere SET @C+=@D+'=@N'+@E+' SELECT @'. Il @Nè dentro le virgolette rendendo al di fuori del campo di applicazione quando si esegue @C. Inoltre penso che
finirai

Ora l'ho provato nel 2012. Dovrebbe funzionare.
segna il

2
Funziona bene ora :) Un paio di posti dove puoi radere alcuni personaggi. Prova a usare CONCATper costruire le tue stringhe. Quindi puoi rilasciare la CONVERTs. Prova SELECT @+=1,@C+=CONCAT(...),@D+=CONCAT(...),@E+=CONCAT(...)nel tuo WHILEciclo. Dovrebbe salvarti un numero ragionevole
MickyT
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.