introduction
Observons la séquence suivante (entiers non négatifs):
0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, ...
Par exemple, prenons les trois premiers chiffres. Ce sont 0, 1, 2
. Les numéros utilisés dans cette séquence peuvent être classés de six manières différentes:
012 120
021 201
102 210
Supposons donc que F (3) = 6 . Un autre exemple est F (12) . Il contient les chiffres:
0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11
Ou la version concaténée:
01234567891011
Pour trouver le nombre de façons de réorganiser cela, nous devons d'abord regarder la longueur de cette chaîne. La longueur de cette chaîne est 14
. Nous calculons donc 14! . Cependant, par exemple, ceux-ci peuvent échanger des places sans interrompre la chaîne finale. Il y a 2 zéros, donc il y en a 2! façons d'échanger les zéros sans perturber la commande. Il y en a aussi 4, donc il y en a 4! façons de changer celles-là. Nous divisons le total par ces deux nombres:
Cela a 14! / (4! × 2!) = 1816214400 façons d'organiser la chaîne 01234567891011
. On peut donc conclure que F (12) = 1816214400 .
La tâche
Étant donné N , sortie F (N) . Pour ceux qui n'ont pas besoin de l'introduction. Pour calculer F (N), nous concaténons d'abord les N premiers entiers non négatifs (par exemple pour N = 12, la chaîne concaténée serait 01234567891011
) et calculons le nombre de façons d'organiser cette chaîne.
Cas de test
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
Remarque
Le calcul de la réponse doit être calculé dans un délai de 10 secondes , le forçage brutal est interdit .
C'est du code-golf , donc la soumission avec le moins d'octets gagne!
10
correcte? Il semble qu'il devrait être inférieur à 10!, Car c'est là que les chiffres répétitifs commencent.10
chiffres sont0, 1, 2, 3, 4, 5, 6, 7, 8, 9
. Dix chiffres différents, donc le résultat est 10!.0
affaire jette mon compte (stupides chaînes vides).F(N)
n'est pasO(N!)
etlog F(N)
est ,O(log N!)
mais ce ne sont que des pressentiments ...Réponses:
Gelée,
1715 octetsEssayez-le en ligne! ou vérifiez tous les cas de test à la fois .
Comment ça fonctionne
la source
ES6,
1188178 octetsQuelqu'un est obligé de me dire qu'il existe un moyen plus court de concaténer les nombres jusqu'à
n
.Économisez 37 octets en prenant l'idée de @ edc65 et en l'exécutant sur des stéroïdes. (Enregistrez un octet supplémentaire en utilisant '|' au lieu de
&&
mais cela limite le résultat à 31 bits.)Edit: encore 3 octets enregistrés grâce à @ edc65.
la source
reduce
:n=>[...[...Array(n).keys()].join``].reduce((r,c,i)=>r*++i/(o[c]=-~o[c]),1,o=[])
n=>[...[...Array(n).keys()].join``].map(c=>r/=(o[c]=-~o[c])/i++,o=[],i=r=1)&&r
r/=(...)/i++
est plus précis quer*=i++/(...)
? C'est le golf le plus ridicule que j'aie jamais vu!APL (Dyalog Extended) , 13 octets
Essayez-le en ligne!
Un programme complet. Les usages
⎕IO←0
.Comment ça fonctionne
Le calcul multinomial provient du fait suivant:
la source
MATL , 21 octets
Essayez-le en ligne!
Explication
la source
Python 2,
14213710197 octets(Merci @adnan pour la suggestion
input
)(Appliqué le calcul incrémental de la version C )
Version originale utilisant factorielle
Vraiment, le seul golf dans ce qui précède appelle
math.factorial
F
et laisse de côté certains espaces, il y a donc probablement une solution de python plus courte.Si une explication est nécessaire,
v
conserve un décompte de la fréquence de chaque chiffre; le décompte est mis à jour pour chaque chiffre de chaque numéro dans la plage indiquée.Dans la version originale, nous calculons le nombre de permutations en utilisant la formule standard (Σf i )! / Π (f i !). Pour la version actuelle, ce calcul se fait de manière incrémentale en répartissant les multiplications et les divisions comme on voit les chiffres. Il n'est peut-être pas évident que la division entière sera toujours exacte, mais il est facile de prouver sur la base de l'observation que chaque division par
k
doit suivrek
multiplications d'entiers consécutifs, donc l'une de ces multiplications doit être divisible park
. (C'est une intuition, pas une preuve.)La version originale est plus rapide pour les gros arguments car elle ne divise que 10 bignums. Bien que la division d'un bignum par un petit entier soit plus rapide que la division d'un bignum par un bignum, lorsque vous avez des milliers de divisions de bignum, cela devient un peu lent.
la source
Python 2, 197 octets (modification: enregistré 4 octets, merci Thomas Kwa!)
Non golfé:
la source
range(0,10)
peut êtrerange(10)
.CJam,
2119 octetsTestez-le ici.
Explication
la source
JavaScript (ES6), 100
Tester
la source
k[c]=~-k[c]
synonyme de--k[c]
?Pyth, 18 octets
Essayez-le en ligne: Démonstration
la source
Haskell, 92 octets
Exemple d'utilisation:
h 12
->1816214400
.Comment ça fonctionne
la source
C,
236174138121 121 octetsBeaucoup de crédit à rici, pour la réduction massive d'octets.
Non golfé
Essayez-le ici .
la source
#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);}
for(;m<10;)s+=b[m],d*=f(b[m++])
mais je pense que c'est quelques octets de plus.C / bc,
233121112 octets ( en supposant 3 pénalité d'octets pour|bc
)Inspiré par Cole Cameron, a supprimé la manipulation de caractère hacky et juste faire de l'arithmétique sur la valeur de l'argument.
Changé en scanf en utilisant le vecteur arg.
Doit
bc
réellement faire le calcul de précision arbitraire.Non golfé et sans avertissement:
Illustré (dont je fais confiance montre l'algorithme):
Et, avec le tuyau passant par bc (et en ajoutant le calcul de F (1000):
Cela a calculé F (5000) - un nombre de 18 592 chiffres - en moins de 10 secondes.
la source
Perl 6, 117 octets
et dans un style plus lisible
la source
Perl 5, 108 octets
Un grand merci à dev-null pour m'avoir sauvé 17 octets, et à japhy pour l'idée factorielle.
la source
05AB1E ,
131211 octetsEssayez-le en ligne!
la source
Python 2 , 123 octets
Essayez-le en ligne!
range
de l'entrée en une seule chaînela source
PowerShell, 125 octets
Prend l'entrée
$args[0]
, soustrait1
, construit une plage d'entiers à partir de0..
ce nombre,-join
s qui ensemble dans une chaîne, et l'enregistre sous$b
. Nous prenons le.Length
de cette chaîne, construisons une autre plage à partir de1..
cette longueur,-join
ces entiers avec*
, puis redirigeons cela versInvoke-Expression
(similaire àeval
). En d'autres termes, nous avons construit la factorielle de la longueur de la séquence de nombres en fonction de l'entrée. Voilà notre numérateur.Nous divisons cela
/
par ...Notre dénominateur, qui est construit en prenant une plage
0..9
et en l'envoyant via une boucle for|%{...}
. À chaque itération, nous définissons une variable d'assistance$c
égale au nombre de fois où le chiffre actuel$_
apparaît à l'intérieur$b
grâce à l' appel .NET[regex]::matches
couplé à l'.count
attribut. Nous construisons ensuite une nouvelle plage allant1..
jusqu'à cette valeur, tant qu'elle n'est pas nulle. Oui, dans de nombreux cas, cela se traduira par une plage1..1
, qui est évaluée à juste1
. Nous prenons tous ces éléments et-join
eux ensemble*
, puis nous les redirigeonsInvoke-Expression
. En d'autres termes, nous avons construit le produit des factorielles du nombre d'occurrences de chaque chiffre.NB
Gère l'entrée
90
sans problème et en moins d'une seconde.... au-delà, cela donne
Infinity
comme sortie, car la longueur de la chaîne permutable résulte en170!
ce qui correspond audouble
type de données (7.25741561530799E+306
), mais171!
ne le fait pas. PowerShell a une ... bizarrerie ... qui monte automatiquement de[int]
à[double]
en cas de débordement (à condition que vous n'ayez pas explicitement casté la variable pour commencer). Non, je ne sais pas pourquoi il ne va pas[long]
pour les valeurs entières.Si nous faisions un casting et une manipulation explicites (par exemple, en utilisant
[uint64]
, pour des entiers 64 bits non signés), nous pourrions obtenir cela plus haut, mais cela alourdirait considérablement le code car nous aurions besoin d'une plage allant jusqu'à 170 avec des conditions, puis une refonte chaque multiplication à partir de là. Comme le défi ne spécifie pas de plage supérieure, je suppose que cela est adéquat.la source
Perl6
Plutôt non golfé pour le moment - besoin de dormir maintenant.
la source
Groovy, 156 octets
Ma première solution humble Code Golf. Vous pouvez le tester ici.
Et voici une version plus lisible:
Assez simple, mais il y a eu quelques points saillants pour moi:
Effectuer une injection / réduction d'un tableau de
chars
à unMap<Character, Integer>
. C'était encore un peu compliqué par l'absence d'une valeur par défaut pour les valeurs de la carte. Ce doute que cela est possible, mais si la carte a par défaut toutes les valeurs à 0, je pourrais éviter le ternaire qui est nécessaire pour éviter un NPE.L'opérateur de propagation Groovy (par exemple
}*.value
) est toujours amusant à utiliserSur la caractéristique ennuyeuse, cependant, était la nécessité de déclarer la fonction factorielle avec le type de retour
BigInteger
. J'avais l'impression que Groovy enveloppait tous les chiffres dansBigInteger
ouBigDecimal
, mais cela pourrait ne pas être le cas lorsqu'il s'agit de renvoyer des types. Je vais devoir expérimenter davantage. Sans ce type de retour explicitement indiqué, nous obtenons très rapidement des valeurs factorielles incorrectes.la source
J, 33 octets
Convertit la plage en une chaîne de chiffres, compte chaque chiffre et applique le coefficient multinomial pour calculer le résultat.
Usage
la source
R, 118 octets
Environ 8 mois de retard pour la fête, mais j'ai pensé que j'allais essayer car cela ressemblait à un défi intéressant.
Essayez-le sur R-fiddle
Expliqué
0 ... n-1
et réduisez-le en une chaîne:paste(1:n-1,collapse="")
x
):x=as.numeric(el(strsplit(...,"")))
factorial(sum(1|x))
qui est juste#digits!
Pour calculer le dénominateur, nous utilisons
table
pour construire un tableau de contingence qui répertorie les fréquences. Dans le cas de F (12) la table générée est:Ce qui signifie que nous pouvons prendre l'utilisation
factorial()
(qui est d'ailleurs vectorisée) sur le compte et simplement prendre le produit:prod(factorial(table(x)))
Remarque: les étapes 4 et 5 ne sont exécutées que dans le cas
n>0
contraire1
.la source
Mathematica, 65 octets
Pourrait probablement être joué au golf plus loin.
la source
Ruby , 64 octets
Essayez-le en ligne!
la source
Stax , 12 octets
Exécutez-le et déboguez-le sur staxlang.xyz!
Déballé (14 octets) et explication:
la source
Gelée , 11 octets
Réponse de Jelly Golfed 15 octets Jelly ...
Un lien monadique acceptant un entier non négatif qui donne un entier positif.
Essayez-le en ligne! Ou consultez la suite de tests .
Comment?
la source
Python 2 , 190 octets
Essayez-le en ligne!
la source
Python 2 , 134 octets
Essayez-le en ligne!
Une approche alternative ...
la source