Je deviens fou: Où est la fonction Ruby pour factorielle? Non, je n'ai pas besoin d'implémentations de tutoriel, je veux juste la fonction de la bibliothèque. Ce n'est pas en Maths!
Je commence à douter, est-ce une fonction de bibliothèque standard?
Il n'y a pas de fonction factorielle dans la bibliothèque standard.
Comme c'est mieux
(1..n).inject(:*) || 1
Ce n'est pas dans la bibliothèque standard mais vous pouvez étendre la classe Integer.
class Integer
def factorial_recursive
self <= 1 ? 1 : self * (self - 1).factorial
end
def factorial_iterative
f = 1; for i in 1..self; f *= i; end; f
end
alias :factorial :factorial_iterative
end
N.B. La factorielle itérative est un meilleur choix pour des raisons évidentes de performances.
Crépité sans vergogne de http://rosettacode.org/wiki/Factorial#Ruby , mon préféré est
class Integer
def fact
(1..self).reduce(:*) || 1
end
end
>> 400.fact
=> 64034522846623895262347970319503005850702583026002959458684445942802397169186831436278478647463264676294350575035856810848298162883517435228961988646802997937341654150838162426461942352307046244325015114448670890662773914918117331955996440709549671345290477020322434911210797593280795101545372667251627877890009349763765710326350331533965349868386831339352024373788157786791506311858702618270169819740062983025308591298346162272304558339520759611505302236086810433297255194852674432232438669948422404232599805551610635942376961399231917134063858996537970147827206606320217379472010321356624613809077942304597360699567595836096158715129913822286578579549361617654480453222007825818400848436415591229454275384803558374518022675900061399560145595206127211192918105032491008000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
Cette implémentation s'avère également être la plus rapide parmi les variantes répertoriées dans le code Rosetta.
Ajoutée || 1
pour gérer le cas zéro.
Merci et appréciation à Mark Thomas , voici une version un peu plus efficace, élégante et obscure:
class Integer
def fact
(2..self).reduce(1,:*)
end
end
Vous pouvez également utiliser Math.gamma
fonction qui se résume à factorielle pour les paramètres entiers.
class Integer
def !
(1..self).inject(:*)
end
end
!3 # => 6
!4 # => 24
En mathématiques, factorial of n
N'est que le gamma function of n+1
(voir: http://en.wikipedia.org/wiki/Gamma_function )
Ruby a Math.gamma()
alors utilisez simplement Math.gamma(n+1)
et convertissez-le en entier si vous le souhaitez.
Je ferais
(1..n).inject(1, :*)
Je viens d'écrire le mien:
def fact(n)
if n<= 1
1
else
n * fact( n - 1 )
end
end
Vous pouvez également définir une factorielle descendante:
def fall_fact(n,k)
if k <= 0
1
else
n*fall_fact(n - 1, k - 1)
end
end
En utilisant Math.gamma.floor
est un moyen simple de produire une approximation, puis de l'arrondir au résultat entier correct. Devrait fonctionner pour tous les nombres entiers, inclure une vérification d'entrée si nécessaire.
def factorial(n=0)
(1..n).inject(:*)
end
factorial(3)
factorial(11)
Vous trouverez probablement un Ruby demande de fonctionnalité utile. Il contient un non trivial patch qui inclut un script Bash démo =. La différence de vitesse entre une boucle naïve et la solution présentée dans le lot peut être littéralement 100x (cent fois), tout en Ruby pur.
Juste une autre façon de le faire, même si ce n'est vraiment pas nécessaire.
class Factorial
attr_reader :num
def initialize(num)
@num = num
end
def find_factorial
(1..num).inject(:*) || 1
end
end
number = Factorial.new(8).find_factorial
puts number
Voici ma version qui me semble claire même si elle n'est pas aussi propre.
def factorial(num)
step = 0
(num - 1).times do (step += 1 ;num *= step) end
return num
end
C'était ma ligne de test IRB qui montrait chaque étape.
num = 8;step = 0;(num - 1).times do (step += 1 ;num *= step; puts num) end;num
Et encore une autre façon (=
def factorial(number)
number = number.to_i
number_range = (number).downto(1).to_a
factorial = number_range.inject(:*)
puts "The factorial of #{number} is #{factorial}"
end
factorial(#number)
Pourquoi la bibliothèque standard exigerait-elle une méthode factorielle, alors qu'il y a un itérateur intégré à cet effet précis? Il s'appelle upto
.
Non, vous n'avez pas besoin d'utiliser la récursivité, comme le montrent toutes ces autres réponses.
def fact(n)
n == 0 ? 1 : n * fact(n - 1)
end
Au contraire, l'itérateur intégré jusqu'à peut être utilisé pour calculer les factorielles:
factorial = 1
1.upto(10) {|x| factorial *= x }
factorial
=> 3628800
class Integer
def factorial
return self < 0 ? false : self==0 ? 1 : self.downto(1).inject(:*)
#Not sure what other libraries say, but my understanding is that factorial of
#anything less than 0 does not exist.
end
end
Encore une façon de le faire:
# fact(n) => Computes the Factorial of "n" = n!
def fact(n) (1..n).inject(1) {|r,i| r*i }end
fact(6) => 720
Avec un grand respect pour tous ceux qui ont participé et ont passé leur temps à nous aider, je voudrais partager mes repères des solutions énumérées ici. Paramètres:
itérations = 1000
n = 6
user system total real
Math.gamma(n+1) 0.000383 0.000106 0.000489 ( 0.000487)
(1..n).inject(:*) || 1 0.003986 0.000000 0.003986 ( 0.003987)
(1..n).reduce(1, :*) 0.003926 0.000000 0.003926 ( 0.004023)
1.upto(n) {|x| factorial *= x } 0.003748 0.011734 0.015482 ( 0.022795)
Pour n = 10
user system total real
0.000378 0.000102 0.000480 ( 0.000477)
0.004469 0.000007 0.004476 ( 0.004491)
0.004532 0.000024 0.004556 ( 0.005119)
0.027720 0.011211 0.038931 ( 0.058309)