Reorganizando a sequência

23

Introdução

Vamos observar a seguinte sequência (números inteiros não negativos):

0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, ...

Por exemplo, vamos pegar os três primeiros números. Estes são 0, 1, 2. Os números usados ​​nesta sequência podem ser ordenados de seis maneiras diferentes:

012   120
021   201
102   210

Então, digamos que F (3) = 6 . Outro exemplo é F (12) . Este contém os números:

0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11

Ou a versão concatenada:

01234567891011

Para encontrar o número de maneiras de reorganizar isso, primeiro precisamos examinar o comprimento dessa string. O comprimento dessa string é 14. Então calculamos 14! . No entanto, por exemplo, eles podem trocar de lugar sem interromper a sequência final. Existem 2 zeros, então existem 2! maneiras de trocar os zeros sem interromper o pedido. Existem também 4, então existem 4! maneiras de mudar esses. Dividimos o total por estes dois números:

Isso tem 14! / (4! × 2!) = 1816214400 maneiras de organizar a sequência 01234567891011. Portanto, podemos concluir que F (12) = 1816214400 .

A tarefa

Dado N , saída F (N) . Para aqueles que não precisam da introdução. Para calcular F (N), primeiro concatenamos os primeiros N números inteiros não negativos (por exemplo, para N = 12, a sequência concatenada seria 01234567891011) e calculamos o número de maneiras de organizar essa sequência.

Casos de teste

Input:   Output:
0        1
1        1
2        2
3        6
4        24
5        120
6        720
7        5040
8        40320
9        362880
10       3628800
11       119750400
12       1816214400
13       43589145600
14       1111523212800
15       30169915776000

Nota

O cálculo da resposta deve ser calculado dentro de um prazo de 10 segundos ; a força bruta é proibida .

Isso é , então a submissão com a menor quantidade de bytes ganha!

Adnan
fonte
A saída está 10correta? Parece que deve ser menor que 10 !, pois é aí que os dígitos repetidos começam.
Geobits 03/02
@ Geobits Os primeiros 10dígitos são 0, 1, 2, 3, 4, 5, 6, 7, 8, 9. Dez dígitos diferentes, então o resultado é 10 !.
Adnan
Ah, certo. Eu acho que o 0caso estava jogando fora minha conta (estúpidas cordas vazias).
Geobits 03/02
11
Não precisa mais se preocupar com isso. A proposta da brecha estava em +4 quando publiquei o comentário. É agora em +9 .
214 Dennis
11
Aqui está uma pergunta matemática interessante sobre esse quebra-cabeça: Qual é o valor de F (N) em relação a N !? Há vários valores de N para os quais F (N) / F (N-1) <N, mas geralmente é um pouco maior. Tenho certeza que F(N)não é O(N!)e que log F(N)é O(log N!), mas esses são apenas palpites ...
rici

Respostas:

5

Geléia, 17 15 bytes

R’DFµ=€QS;@L!:/

Experimente online! ou verifique todos os casos de teste de uma só vez .

Como funciona

R’DFµ=€QS;@L!:/    Main link. Input: n

R                  Yield [1, ..., n] for n > 0 or [0] for n = 0.
 ’                 Decrement. Yields [0, ..., n - 1] or [-1].
  D                Convert each integer into the list of its decimal digits.
   F               Flatten the resulting list of lists.
    µ              Begin a new, monadic chain. Argument: A (list of digits)
       Q           Obtain the unique elements of A.
     =€            Compare each element of A with the result of Q.
                   For example, 1,2,1 =€ Q -> 1,2,1 =€ 1,2
                                           -> [[1, 0], [0, 1], [1, 0]]
        S          Sum across columns.
                   This yields the occurrences of each unique digit.
         ;@L       Prepend the length of A.
            !      Apply factorial to each.
             :/    Reduce by divison.
                   This divides the first factorial by all remaining ones.
Dennis
fonte
Isso é mesmo geléia? Eu vejo muitos caracteres ASCII :-P
Luis Mendo
3
Eles sempre conseguem esgueirar-se de alguma forma ...
Dennis
10

ES6, 118 81 78 bytes

n=>[...[...Array(n).keys()].join``].map(c=>r/=(o[c]=-~o[c])/i++,o=[],i=r=1)&&r

Alguém pode me dizer que há uma maneira mais curta de concatenar os números até n.

Economizou 37 bytes legais, pegando a idéia de @ edc65 e executando-a em esteróides. (Salve um byte extra usando '|' em vez de, &&mas isso limita o resultado a 31 bits.)

Editar: salvou mais 3 bytes novamente graças a @ edc65.

Neil
fonte
Não encontrou uma maneira de reduzir a concatenação de dígitos. Mas todo o resto pode ser menor
edc65 3/16/16
Salve 2 bytes com reduce:n=>[...[...Array(n).keys()].join``].reduce((r,c,i)=>r*++i/(o[c]=-~o[c]),1,o=[])
user81655
11
Uau! mas 78 é melhor:n=>[...[...Array(n).keys()].join``].map(c=>r/=(o[c]=-~o[c])/i++,o=[],i=r=1)&&r
edc65 04/04
11
@ edc65 r/=(...)/i++é mais preciso do que r*=i++/(...)? Esse é o golfe mais ridículo que eu já vi!
Neil
2
Eu tive que parar por um momento, porque pensei que você tinha um regex lá.
Mama Fun Roll
7

APL (Dyalog Extended) , 13 bytes

×/2!/+\⎕D⍧⍕⍳⎕

Experimente online!

Um programa completo. Usos ⎕IO←0.

Como funciona

×/2!/+\⎕D⍧⍕⍳⎕
               Take input from stdin (N)
               Generate range 0..N-1
               Stringify the entire array (S)
                (The result has spaces between items)
       D       The character array '0123456789'
               Count occurrences of each digit in S
×/2!/+\         Calculate multinomial:
     +\           Cumulative sum
  2!/             Binomial of consecutive pairs
×/                Product

O cálculo multinomial deriva do seguinte fato:

(a1+a2++an)!a1!a2!an!=(a1+a2)!a1!a2!×(a1+a2++an)!(a1+a2)!a3!an!

=(a1+a2)!a1!a2!×(a1+a2+a3)!(a1+a2)!a3!×(a1+a2++an)!(a1+a2+a3)!an!

==(a1+a2a1)(a1+a2+a3a1+a2)(a1++ana1++an1)

Bubbler
fonte
11
E é por isso que os programadores devem aprender matemática.
Anônimo
@Anonymous… e use uma linguagem de programação matematicamente inclinada.
Adám 01/12
5

MATL , 21 bytes

:qV0h!4Y2=sts:pw"@:p/

Experimente online!

Explicação

:q     % implicitly input N, and generate vector [0, 1, ..., N-1]
V      % convert to string representation of numbers. Contains spaces,
       % but no matter. Only characters '0', ..., '9' will be counted
0h     % append 0 character (not '0'), so that string is never empty
!      % convert string to column char array
4Y2    % string '0123456789' (row char array)
=      % test all pairs for equality
s      % sum each column. For N = 12 this gives [2, 4, 1, 1, ..., 1]
t      % duplicate
s      % compute sum. For N = 12 this gives 14
:p     % factorial
w      % swap. Now vector [2, 4, 1, 1, ..., 1] is on top
"      % for each number in that vector
  @:p  %   factorial
  /    %   divide
       % implicitly end loop
       % implicitly display
Luis Mendo
fonte
@Adnan Solved. E com menos bytes :-)
Luis Mendo
Parece muito bom! :)
Adnan
@Adnan Thanks! Eu adicionei uma explicação
Luis Mendo
5

Python 2, 142 137 101 97 bytes

(Obrigado @adnan pela sugestão sobre input)

(Aplicou o cálculo incremental da versão C )

f=1;v=10*[0]
for i in range(input()):
 for h in str(i):k=int(h);v[k]+=1;f=f*sum(v)/v[k]
print f

Versão original usando fatorial

import math
F=math.factorial
v=10*[0]
for i in range(input()):
 for h in str(i):v[int(h)]+=1
print reduce(lambda a,x:a/F(x),v,F(sum(v)))

Realmente, o único jogo de golfe acima é chamar math.factorial Fe deixar alguns espaços, portanto, provavelmente há uma solução python mais curta.

Se for necessária explicação, vmantenha uma contagem da frequência de cada dígito; a contagem é atualizada para cada dígito em cada número no intervalo indicado.

Na versão original, calculamos o número de permutações usando a fórmula padrão (Σf i )! / Π (f i !). Para a versão atual, esse cálculo é feito de forma incremental, distribuindo as multiplicações e divisões conforme vemos os dígitos. Pode não ser óbvio que a divisão de números inteiros será sempre exata, mas é fácil provar com base na observação de que cada divisão kdeve seguir kmultiplicações de números inteiros consecutivos; portanto, uma dessas multiplicações deve ser divisível por k. (Isso é uma intuição, não uma prova.)

A versão original é mais rápida para argumentos grandes porque faz apenas 10 divisões bignum. Embora dividir um bignum por um número inteiro pequeno seja mais rápido do que dividir um bignum por um bignum, quando você tem milhares de bignum divididos, fica um pouco lento.

rici
fonte
f = f * soma (v) / v [k] -> f * = soma (v) / v [k] salva um byte
Mikko Virkkilä 6/6
@ superflux: mas não é o mesmo significado.
rici
5

Python 2, 197 bytes (editar: salvou 4 bytes, obrigado Thomas Kwa!)

import math
l,g,f,p,r,s=[],[],math.factorial,1,range,str
for x in r(int(input())):l.append(s(x))
l="".join(l)
for y in r(10):b=s(l).count(s(y));g.append(f(b));
for c in g:p*=y
print f(int(len(l)))/p

Ungolfed:

import math

l=[] #list of the numbers from 0 to n
exchange_list=[] #numbers that can be exchanged with each other, ie      repeats

multiplied = 1 #for multiplying the digits by each other
n = int(input())

for x in range(n): #put all the numbers from 0-n into the list
    l.append(str(x))

l = "".join(l) #put all the digits in a string to remove repeats

for x in range(10): #look at all the digits and check how many are in the     list/string
    count = str(l).count(str(x))
    if count > 1: #if there is more than 1 of the digit, put the factorial of the amount of - 
        exchange_list.append(math.factorial(count)) # - appearances into the exchange list.

for x in exchange_list: #multiply all the values in the list by each other
    multiplied*=x

print math.factorial(int(len(l)))/multiplied #print the factorial of the  length of the string 
#divided by the exchanges multiplied
Dave Lin
fonte
11
Bem-vindo à Programação de Puzzles e Code Golf! Esta resposta foi sinalizada como VLQ (qualidade muito baixa), desconfio porque não contém nenhuma explicação ou versão não destruída, que é a norma aqui. Supondo que sua resposta funcione, e você a aprimore de ser apenas "código", parece muito bom!
gato
range(0,10)pode ser range(10).
lirtosiast
4

CJam, 21 19 bytes

ri,s_,A,s@fe=+:m!:/

Teste aqui.

Explicação

ri   e# Read input and convert to integer N.
,    e# Get a range [0 1 ... N-1].
s    e# Convert to string, flattening the range.
_,   e# Duplicate and get its length.
A,s  e# Push "012345789".
@fe= e# Pull up the other copy of the string and count the occurrences of each digit.
+    e# Prepend the string length.
:m!  e# Compute the factorial of each of them.
:/   e# Fold division over the list, dividing the factorial of the length by all the other
     e# factorials.
Martin Ender
fonte
3

JavaScript (ES6), 100

n=>(f=[...[...Array(n).keys()].join``].map(c=>(k[c]=~-k[c],p*=i++),i=p=1,k=[]),k.map(v=>p/=f[~v]),p)

Teste

F=n=>(f=[...[...Array(n).keys()].join``].map(c=>(k[c]=~-k[c],p*=i++),i=p=1,k=[]),k.map((v,i)=>p/=f[~v]),p)

// Less golfed
U=n=>( // STEP 1, count digits, compute factorials
      f= // will contain the value of factorials 1 to len of digits string
      [...[...Array(n).keys()].join``] // array of cancatenated digits
      .map(c=> // execute the following for each digit
           (
            k[c]=~-k[c], // put in k[c] the repeat count for digit c, negated 
            p*=i++       // evaluate factorial, will be stored in f
           ),i=p=1,k=[]),// initialisations
       // at the end of step 1 we have all factorials if f and max factorial in p
       // STEP 2, divide the result taking into account the repeated digits
      k.map(v=>p/=f[~v]), // for each digit, divide p by the right factorial (~v === -v-1)
  p // return result in p
) 

// Test
console.log=x=>O.textContent+=x+'\n'

for(j=0;j<=15;j++) console.log(j+' '+F(j))
<pre id=O></pre>

edc65
fonte
Não é k[c]=~-k[c]sinônimo de --k[c]?
Usandfriends
11
@usandfriends não, quando k [c] é indefinido --k [c] é NaN
edc65
Ooh, boa variedade de fatoriais.
Neil
... embora você não precise. Veja minha última atualização.
Neil
3

Pitão, 18 bytes

/F.!M+lJ.njRTQ/LJT

Experimente online: Demonstração

/F.!M+lJ.njRTQ/LJT   implicit: Q = input number
          jRTQ       convert each number in [0, ..., Q-1] to their digits
        .n           flatten to a single list
       J             store this list in J
              /LJT   for each digit count the number of appearances in J
     +lJ             prepend the length of J
  .!M                compute the factorial for each number
/F                   fold by division
Jakube
fonte
3

Haskell, 92 bytes

import Data.List
h n|l<-sort$show=<<[0..n-1]=foldl1 div$product.map fst.zip[1..]<$>l:group l

Exemplo de uso: h 12 -> 1816214400.

Como funciona

l<-sort$show=<<[0..n-1]       -- bind l to the sorted concatenated string
                              -- representations of the numbers from 0 to n-1
                              -- e.g. n=12 -> "00111123456789"

               l: group l     -- group the chars in l and put l itself in front
                              -- e.g. ["00111123456789","00","1111","2",..."9"]
            <$>               -- map over this list
    product.map fst.zip[1..]  -- the faculty the length of the sublist (see below)  
                              -- e.g. [87178291200,2,24,1,1,1,..,1]
foldl1 div                    -- fold integer division from the left into this list
                              -- e.g. 87178291200 / 2 / 24 / 1

                              -- Faculty of the length of a list:
                  zip[1..]    -- make pairs with the natural numbers
                              -- e.g. "1111" -> [(1,'1'),(2,'1'),(3,'1'),(4,'1')]
          map fst             -- drop 2nd element form the pairs
                              -- e.g. [1,2,3,4]
  product                     -- calculate product of the list
nimi
fonte
3

C, 236 174 138 121 bytes

Muito crédito para os rici, pela redução maciça de bytes.

long long d,f=1;j,s=1,n,b[10]={1};main(d){for(scanf("%d",&n);n--;)for(j=n;j;j/=10,f*=++s)d*=++b[j%10];printf("%Ld",f/d);}

Ungolfed

long long d,f=1;
j,s=1,n,b[10]={1};

main(d)
{
    scanf("%d",&n); /* get input */
    for(;n--;) /* iterate through numbers... */
        for(j=n;j;j/=10,f*=++s) /* iterate through digits, sum up and factorial */
            d*=++b[j%10]; /* count and factorial duplicates */
    printf("%Ld",f/d); /* print out result */
}

Experimente aqui .

Cole Cameron
fonte
11
Você pode salvar 43 caracteres não mexendo com -lm. Basta contar os dígitos que você os encontra:#define L long long L d;i,j,k,m,n,s=1,b[10]={1};L f(n){return n?n*f(n-1):1;}main(d){for(scanf("%d",&n);i<n;)for(j=i++;j;j/=10)++b[j%10],++s;for(;m<10;)d*=f(b[m++]);printf("%Ld",f(s)/d);}
rici
Você também pode contá-los no loop em que calcula d: for(;m<10;)s+=b[m],d*=f(b[m++])mas acho que são mais alguns bytes.
rici
Isso é brilhante. Vou combinar com meus esforços atuais de golfe e editar.
5116 Cole Cameron
Bom: dê uma olhada na minha para ver como integrar a computação fatorial no loop original, que tem a vantagem de trabalhar em uma faixa um pouco maior se você não tiver aritmética de precisão arbitrária. Eu acho que são outros 20 bytes para fazer a barba.
rici
3

C / bc, 233 121 112 bytes (assumindo penalidade de 3 bytes |bc)

  1. Inspirado por Cole Cameron, removeu a manipulação de caracteres hacky e apenas faz aritmética no valor do argumento.

  2. Alterado para scanf usando o vetor arg.

    C[10]={1},n=1,k,t;main(){for(scanf("%d",&k);k--;)for(t=k;t;t/=10)printf("%d/%d*",++n,++C[t%10]);puts("1");}
    

Necessidades bc realmente fazer o cálculo de precisão arbitrário.

Ungolfed e aviso livre:

#include <stdio.h>
int main() {
  int C[10]={1},n=1,k,t;    /* 0 is special-cased */
  for(scanf("%d",&k);k--;)  /* For each integer less than k */
    for(int t=k;t;t/=10)    /* For each digit in t */
      printf("%d/%d*",++n,++C[t%10]);  /* Incremental choice computation */
  puts("1");                /* Finish the expression */
}

Ilustrado (que eu confio mostra o algoritmo):

$ for i in {0..15} 100 ; do printf %4d\  $i;./cg70892g<<<$i;done
   0 1
   1 1
   2 2/1*1
   3 2/1*3/1*1
   4 2/1*3/1*4/1*1
   5 2/1*3/1*4/1*5/1*1
   6 2/1*3/1*4/1*5/1*6/1*1
   7 2/1*3/1*4/1*5/1*6/1*7/1*1
   8 2/1*3/1*4/1*5/1*6/1*7/1*8/1*1
   9 2/1*3/1*4/1*5/1*6/1*7/1*8/1*9/1*1
  10 2/1*3/1*4/1*5/1*6/1*7/1*8/1*9/1*10/1*1
  11 2/1*3/2*4/1*5/1*6/1*7/1*8/1*9/1*10/1*11/1*12/2*1
  12 2/1*3/2*4/3*5/2*6/1*7/1*8/1*9/1*10/1*11/1*12/1*13/1*14/4*1
  13 2/1*3/1*4/2*5/3*6/4*7/2*8/1*9/1*10/1*11/1*12/1*13/1*14/1*15/2*16/5*1
  14 2/1*3/1*4/2*5/1*6/3*7/4*8/5*9/2*10/1*11/1*12/1*13/1*14/1*15/1*16/2*17/2*18/6*1
  15 2/1*3/1*4/2*5/1*6/3*7/1*8/4*9/5*10/6*11/2*12/1*13/1*14/1*15/1*16/1*17/2*18/2*19/2*20/7*1
 100 2/1*3/2*4/3*5/1*6/4*7/1*8/5*9/1*10/6*11/1*12/7*13/1*14/8*15/1*16/9*17/1*18/10*19/1*20/11*21/2*22/2*23/12*24/3*25/4*26/5*27/2*28/6*29/2*30/7*31/2*32/8*33/2*34/9*35/2*36/10*37/2*38/11*39/2*40/12*41/3*42/3*43/13*44/4*45/13*46/5*47/6*48/7*49/3*50/8*51/3*52/9*53/3*54/10*55/3*56/11*57/3*58/12*59/3*60/13*61/4*62/4*63/14*64/5*65/14*66/6*67/14*68/7*69/8*70/9*71/4*72/10*73/4*74/11*75/4*76/12*77/4*78/13*79/4*80/14*81/5*82/5*83/15*84/6*85/15*86/7*87/15*88/8*89/15*90/9*91/10*92/11*93/5*94/12*95/5*96/13*97/5*98/14*99/5*100/15*101/6*102/6*103/16*104/7*105/16*106/8*107/16*108/9*109/16*110/10*111/16*112/11*113/12*114/13*115/6*116/14*117/6*118/15*119/6*120/16*121/7*122/7*123/17*124/8*125/17*126/9*127/17*128/10*129/17*130/11*131/17*132/12*133/17*134/13*135/14*136/15*137/7*138/16*139/7*140/17*141/8*142/8*143/18*144/9*145/18*146/10*147/18*148/11*149/18*150/12*151/18*152/13*153/18*154/14*155/18*156/15*157/16*158/17*159/8*160/18*161/9*162/9*163/19*164/10*165/19*166/11*167/19*168/12*169/19*170/13*171/19*172/14*173/19*174/15*175/19*176/16*177/19*178/17*179/18*180/19*181/10*182/20*183/20*184/20*185/20*186/20*187/20*188/20*189/20*190/20*1

E, com o tubo através de bc (e adicionando o cálculo de F (1000):

$ time for i in {0..15} 100 1000; do printf "%4d " $i;./cg70892g<<<$i|bc;done
   0 1
   1 1
   2 2
   3 6
   4 24
   5 120
   6 720
   7 5040
   8 40320
   9 362880
  10 3628800
  11 119750400
  12 1816214400
  13 43589145600
  14 1111523212800
  15 30169915776000
 100 89331628085599251432057142025907698637261121628839475101631496666431\
15835656928284205265561741805657733401084399630568002336920697364324\
98970890135552420133438596044287494400000000
1000 45200893173828954313462564749564394748293201305047605660842814405721\
30092686078003307269244907986874394907789568742409099103180981532605\
76231293886961761709984429587680151617686667512237878219659252822955\
55855915137324368886659115209005785474446635212359968384367827713791\
69355041534558858979596889046036904489098979549000982849236697235269\
84664448178907805505235469406005706911668121136625035542732996808166\
71752374116504390483133390439301402722573240794966940354106575288336\
39766175522867371509169655132556575711715087379432371430586196966835\
43089966265752333684689143889508566769950374797319794056104571082582\
53644590587856607528082987941397113655371589938050447115717559753757\
79446152023767716192400610266474748572681254153493484293955143895453\
81280908664541776100187003079567924365036116757255349569574010994259\
42252682660514007543791061446917037576087844330206560326832409035999\
90672829766080114799705907407587600120545365651997858351981479835689\
62520355320273524791310387643586826781881487448984068291616884371091\
27306575532308329716263827084514072165421099632713760304738427510918\
71188533274405854336233290053390700237606793599783757546507331350892\
88552594944038125624374807070741486495868374775574664206439929587630\
93667017165594552704187212379733964347029984154761167646334095514093\
41014074159155080290000223139198934433986437329522583470244030479680\
80866686589020270883335109556978058400711868633837851169536982150682\
22082858700246313728903459417761162785473029666917398283159071647546\
25844593629926674983035063831472139097788160483618679674924756797415\
01543820568689780263752397467403353950193326283322603869951030951143\
12095550653333416019778941123095611302340896001090093514839997456409\
66516109033654275890898159131736630979339211437991724524614375616264\
98121300206207564613016310794402755159986115141240217861695468584757\
07607748055900145922743960221362021598547253896628914921068009536934\
53398462709898222067305585598129104976359039062330308062337203828230\
98091897165418693363718603034176658552809115848560316073473467386230\
73804128409097707239681863089355678037027073808304307450440838875460\
15170489461680451649825579772944318869172793737462142676823872348291\
29912605105826175323042543434860948610529385778083808434502476018689\
05150440954486767102167489188484011917026321182516566110873814183716\
30563399848922002627453188732598763510259863554716922484424965400444\
85477201353937599094224594031100637903407963255597853004241634993708\
88946719656130076918366596377038503741692563720593324564994191848547\
42253991635763101712362557282161765775758580627861922528934708371322\
38741942406807912441719473787691540334781785897367428903185049347013\
44010772740694376407991152539070804262207515449370191345071234566501\
33117923283207435702471401696679650483057129117719401161591349048379\
16542686360084412816741479754504459158308795445295721744444794851033\
08800000000

real    0m0.246s
user    0m0.213s
sys     0m0.055s

Isso calculou F (5000) - um número de 18.592 dígitos - em menos de 10 segundos.

$ time ./cg70892g3<<<5000|BC_LINE_LENGTH=0 bc|wc -c
18593

real    0m9.274s
user    0m9.273s
sys     0m0.005s
rici
fonte
3

Perl 6, 117 bytes

say $_ <2??1!!permutations(+[(my@n=^$_ .join.comb)]).elems÷[*] ([*] 2..$_ for @n.classify(&unique).values)for lines

e em um fasion mais legível

for (lines) -> $number {
    say 1 and next if $number < 2;
    my @digits = (^$number).join.comb;
    my @duplicates = @digits.classify(&unique).values;
    my $unique_permutations = permutations(+@digits).elems ÷ [*] ([*] 2..$_ for @duplicates);
    say $unique_permutations;
}
Joshua
fonte
3

Perl 5, 108 bytes

sub f{eval join"*",@_,1}push@a,/./g for 0..<>-1;for$i(0..9){$b[$i]=grep/$i/,@a}say f(1..@a)/f map{f 1..$_}@b

Muito obrigado a dev-null por me salvar 17 bytes e a japhy pela idéia fatorial.

msh210
fonte
3

05AB1E , 13 12 11 bytes

ÝD¨SāPr¢!P÷

Experimente online!

Ý             # range [0..input]
 D            # duplicate
  ¨           # drop the last element
   S          # split into digits
    ā         # length range: [1..number of digits]
     P        # product (effectively a factorial)
      r       # reverse the stack
       ¢      # count occurences of each number in the list of digits
        !     # factorial of each count
         P    # product of those
          ÷   # divide the initial factorial by this product
Grimmy
fonte
3

Python 2 , 123 bytes

import math
i,b,F="".join(map(str,range(input()))),1,math.factorial
for x in range(10):b*=F(i.count(`x`))
print F(len(i))/b

Experimente online!

  1. Converta a rangeentrada em uma única sequência
  2. Verifique quantas vezes cada um dos números de 0 a 9 aparece na sequência e obtenha o fatorial para cada um e multiplique-os juntos
  3. Divida o fatorial do comprimento da sequência pelo número calculado na etapa 2
ElPedro
fonte
2

PowerShell, 125 bytes

(1..(($b=0..($args[0]-1)-join'').Length)-join'*'|iex)/((0..9|%{$c=[regex]::Matches($b,$_).count;1..($c,1)[!$c]})-join'*'|iex)

Pega entrada $args[0], subtrai 1, cria um intervalo de números inteiros a partir 0..desse número, -joins que juntos em uma string e salva como $b. Pegamos a .Lengthstring, construímos outro intervalo a partir 1..desse comprimento, -joinesses números inteiros juntos e *, em seguida, canalizamos isso paraInvoke-Expression (semelhante aeval ). Em outras palavras, construímos o fatorial do comprimento da sequência numérica com base na entrada. Esse é o nosso numerador.

Nós dividimos isso / por ...

Nosso denominador, que é construído pegando um intervalo 0..9e enviando-o através de um loop for |%{...}. A cada iteração, definimos uma variável auxiliar $cigual ao número de vezes que o dígito atual $_aparece dentro, $bgraças à chamada do .NET[regex]::matches associada ao .countatributo Em seguida, construímos um novo intervalo 1..até esse valor, desde que não seja zero. Sim, em muitos casos, isso resultará em um intervalo 1..1, que é avaliado apenas 1. Nós levamos todos -joineles e eles juntos *e depois canalizamos paraInvoke-Expression novamente. Em outras palavras, construímos o produto dos fatoriais do número de ocorrências de cada dígito.


NB

Lida com entradas 90sem problemas e em menos de um segundo.

PS C:\Tools\Scripts\golfing> .\rearranging-the-sequence.ps1 90
1.14947348910454E+159

PS C:\Tools\Scripts\golfing> Measure-Command {.\rearranging-the-sequence.ps1 90} | FL TotalMilliseconds
TotalMilliseconds : 282.587

... além disso resulta em Infinitysaída, pois o comprimento da string permutável resulta no 170!qual se encaixa no doubletipo de dados ( 7.25741561530799E+306), mas 171!não. O PowerShell tem uma ... peculiaridade ... que faz a conversão automática automaticamente de [int]para [double]no caso de estouro (desde que você não tenha explicitamente convertido a variável para começar). Não, não sei por que ele não é usado [long]para valores inteiros.

Se fizermos alguma conversão e manipulação explícitas (por exemplo, usar [uint64] números inteiros de 64 bits não assinados), poderíamos obter um valor mais alto, mas isso aumentaria significativamente o código, pois precisaríamos atingir até 170 comprimentos com condicionais e, em seguida, reformular cada multiplicação a partir daí. Como o desafio não especifica um intervalo superior, presumo que isso seja adequado.

AdmBorkBork
fonte
2

Perl6

perl6 -e 'sub p ($a) { my $x = $a.join.comb.classify(+*).values.map(*.elems).classify(+*).values.flatmap(*.list).flatmap((2..+*).list); my $y = 2..$a[*-1]; [/] $x.list * [*] $y.list }; p([1..11]).say'

Bastante não-destruído no momento - precisa dormir agora.

user52889
fonte
2

Groovy, 156 bytes

def f(n){def s=(0..n-1).join('')
0==n?1:g(s.size())/s.inject([:]){a,i->a[i]=a[i]?a[i]+1:1;a}*.value.inject(1){a,i->a*g(i)}}
BigInteger g(n){n<=1?1:n*g(n-1)}

Minha humilde primeira solução Code Golf. Você pode testá-lo aqui.

E aqui está uma versão mais legível:

def f(n) {
  def s = (0..n - 1).join('')                       // Store our concatented range, s
  0 == n ? 1 :                                      // Handle annoying case where n = 0
    fact(s.size()) / s.inject([:]) {                // Divide s.size()! by the product of the values we calculate by...
      a, i ->                                       // ...reducing into a map...
        a[i] = a[i] ? a[i] + 1 : 1                  // ...the frequency of each digit
        a                                           // Our Groovy return statement
    }*.value.inject(1) { a, i -> a * fact(i) }      // Finally, take the product of the factorial of each frequency value
}

BigInteger fact(n) { n <= 1 ? 1 : n * fact(n - 1) } // No built-in factorial function...

Bem direto, mas havia alguns destaques para mim:

  • Executando uma injeção / redução de uma matriz de charspara a Map<Character, Integer>. Isso ainda foi um pouco complicado pela falta de um valor padrão para os valores do mapa. Essa dúvida é possível, mas se o mapa padronizar todos os valores para 0, eu poderia evitar o ternário necessário para evitar um NPE.

  • O operador de expansão Groovy (por exemplo, }*.value ) é sempre divertido de usar

No aspecto irritante, porém, havia a necessidade de declarar a função fatorial com o tipo de retorno BigInteger. Fiquei com a impressão de que o Groovy colocou todos os números em BigIntegeror BigDecimal, mas talvez não seja esse o caso quando se trata de retornar tipos. Vou ter que experimentar mais. Sem esse tipo de retorno explicitamente declarado, obtemos valores fatoriais incorretos muito rapidamente.

Zelândia
fonte
2

J, 33 bytes

(#(%*/)&:!&x:#/.~)@([:;<@":"0)@i.

Converte o intervalo em uma sequência de dígitos, conta cada dígito e aplica o coeficiente multinomial para calcular o resultado.

Uso

   f =: (#(%*/)&:!&x:#/.~)@([:;<@":"0)@i.
   (,.f"0) i. 16
 0              1
 1              1
 2              2
 3              6
 4             24
 5            120
 6            720
 7           5040
 8          40320
 9         362880
10        3628800
11      119750400
12     1816214400
13    43589145600
14  1111523212800
15 30169915776000
milhas
fonte
2

R, 118 bytes

Cerca de 8 meses atrasado para a festa, mas pensei em tentar, porque parecia um desafio interessante.

function(n,x=as.numeric(el(strsplit(paste(1:n-1,collapse=""),""))),F=factorial)`if`(n,F(sum(1|x))/prod(F(table(x))),1)

Experimente no R-fiddle

Explicado

  1. Gere um vetor 0 ... n-1e recolha-o em uma sequência:paste(1:n-1,collapse="")
  2. Divida a string em seus dígitos e converta para numérico (armazene como x):x=as.numeric(el(strsplit(...,"")))
  3. Para calcular o numerador, simplesmente fazemos o factorial(sum(1|x))que é apenas#digits!
  4. Para calcular o denominador, utilizamos tablepara construir uma tabela de contingência que lista as frequências. No caso de F (12), a tabela gerada é:

    0 1 2 3 4 5 6 7 8 9 
    2 4 1 1 1 1 1 1 1 1 
    
  5. O que significa que podemos usar o uso factorial()(que por sinal é vetorizado) na contagem e simplesmente levar o produto:prod(factorial(table(x)))

Nota: os passos 4 e 5 são realizados somente se n>0retornar 1.

Billywob
fonte
1

Mathematica, 65 bytes

(Tr@IntegerLength[a=Range@#-1]+1)!/Times@@(Total[DigitCount@a]!)&

Provavelmente poderia ser jogado ainda mais.

LegionMammal978
fonte
1

Stax , 12 bytes

éÄ\↑≈g→FP○░→

Execute e depure-o em staxlang.xyz!

Descompactado (14 bytes) e explicação:

r$c%|Fso:GF|F/
r                 Range [0..input)
 $                Stringify each and concat
  c               Copy atop the stack
   %|F            Factorial of length
      s           Swap original back to top
       o          Sort
        :G        Run lengths
          F       For each:
           |F       Factorial
             /      Divide running quotient by this factorial
                  Implicit print
Khuldraeseth na'Barya
fonte
1

Gelatina , 11 bytes

Resposta de Jelly Golfed Dennis '15 byte ...

ḶDFµW;ĠẈ!:/

Um link monádico que aceita um número inteiro não negativo que gera um número inteiro positivo.

Experimente online! Ou veja a suíte de testes .

Quão?

ḶDFµW;ĠẈ!:/ - Link: non-negative integer, N   e.g. 12
Ḷ           - lowered range            [0,1,2,3,4,5,6,7,8,9,10,11]
 D          - to decimal (vectorises)  [[0],[1],[2],[3],[4],[5],[6],[7],[8],[9],[1,0],[1,1]]
  F         - flatten                  [0,1,2,3,4,5,6,7,8,9,1,0,1,1]
   µ        - start a new monadic chain - i.e. f(that)
    W       - wrap in a list           [[0,1,2,3,4,5,6,7,8,9,1,0,1,1]]
      Ġ     - group indices by values  [[1,12],[2,11,13,14],3,4,5,6,7,8,9,10]
     ;      - concatenate              [[0,1,2,3,4,5,6,7,8,9,1,0,1,1],[1,12],[2,11,13,14],3,4,5,6,7,8,9,10]
       Ẉ    - length of each           [14,2,4,1,1,1,1,1,1,1,1]
        !   - factorial (vectorises)   [87178291200,2,24,1,1,1,1,1,1,1,1]
          / - reduce by:
         :  -   integer division       1816214400
Jonathan Allan
fonte
0

Python 2 , 190 bytes

from collections import*
g,n=range,int(input())
p=lambda r:reduce(lambda x,y:x*y,r,1)
f=lambda n:p(g(1,n+1))
s=''.join(str(i)for i in g(n))
c=Counter(s)
print(f(len(s))/p(f(c[i])for i in c))

Experimente online!

Alexey Burdin
fonte
0

Python 2 , 134 bytes

s="".join(map(str,range(input())))
n=d=1
for i in range(1,len(s)+1):n*=i;d*=i**len([c for c in range(10)if s.count(`c`)>=i])
print n/d

Experimente online!

Uma abordagem alternativa ...

Chas Brown
fonte