Is er een methode die een factoriële in Java berekent?

Ik heb het nog niet gevonden. Heb ik iets gemist?
Ik weet dat een faculteit methode een algemeen voorbeeldprogramma voor beginners is. Maar zou het niet handig zijn om een ​​standaard implementatie te hebben voor deze om opnieuw te gebruiken?
Ik zou een dergelijke methode kunnen gebruiken met standaardtypen (bijv. Int, Long …) en met Biginteger / BigDecimal, ook.


Antwoord 1, Autoriteit 100%

Ik denk niet dat het nuttig zou zijn om een ​​bibliotheekfunctie te hebben voor factorial. Er is veel onderzoek naar efficiënte factoriale implementaties.


Antwoord 2, Autoriteit 231%

Apache Commons Math heeft een paar factoriale methoden in de Mathutils klasse.


Antwoord 3, Autoriteit 154%

public class UsefulMethods {
    public static long factorial(int number) {
        long result = 1;
        for (int factor = 2; factor <= number; factor++) {
            result *= factor;
        }
        return result;
    }
}

Big Numbers-versie door HoldOffhunger :

public static BigInteger factorial(BigInteger number) {
    BigInteger result = BigInteger.valueOf(1);
    for (long factor = 2; factor <= number.longValue(); factor++) {
        result = result.multiply(BigInteger.valueOf(factor));
    }
    return result;
}

Antwoord 4, Autoriteit 88%

Bare naakte factoren zijn in de praktijk zelden nodig. Meestal heb je een van de volgende dingen nodig:

1) Verdeel een factorial door een ander of

2) Aantal benaderd drijvend antwoord.

In beide gevallen zou je beter zijn met eenvoudige aangepaste oplossingen.

In het geval (1), zeg, als x = 90! / 85!, Dan berekent u het resultaat net zo X = 86 * 87 * 88 * 89 * 90, zonder dat u 90 nodig hebt! in het geheugen 🙂

In het geval (2), Google voor “Stirling’s benadering”.


Antwoord 5, Autoriteit 46%

Gebruik Guava’s BigIntegerMathals volgt:

BigInteger factorial = BigIntegerMath.factorial(n);

(vergelijkbare functionaliteit voor inten longis beschikbaar in IntMathen LongMathrespectievelijk.)


Antwoord 6, Autoriteit 23%

Hoewel factorials een leuke oefening maken voor de beginprogrammeur, ze zijn niet erg nuttig in de meeste gevallen, en iedereen weet hoe iedereen een factoriële functie moet schrijven, dus ze zijn meestal niet in het gemiddelde Bibliotheek.


Antwoord 7, Autoriteit 23%

Ik geloof dat dit de snelste manier zou zijn, door een opzoektabel:

private static final long[] FACTORIAL_TABLE = initFactorialTable();
private static long[] initFactorialTable() {
    final long[] factorialTable = new long[21];
    factorialTable[0] = 1;
    for (int i=1; i<factorialTable.length; i++)
        factorialTable[i] = factorialTable[i-1] * i;
    return factorialTable;
}
/**
 * Actually, even for {@code long}, it works only until 20 inclusively.
 */
public static long factorial(final int n) {
    if ((n < 0) || (n > 20))
        throw new OutOfRangeException("n", 0, 20);
    return FACTORIAL_TABLE[n];
}

Voor het native type long(8 BYTES), kan het alleen vasthouden aan 20!

20! = 2432902008176640000(10) = 0x 21C3 677C 82B4 0000

Uiteraard, 21!zal overflow veroorzaken.

Daarom, voor native type long, is slechts een maximum van 20!toegestaan, zinvol en correct.


Antwoord 8, Autoriteit 23%

Omdat faculteit zo snel groeit, is Stack Overflow geen probleem als u recursie gebruikt. In feite, de waarde van 20! is de grootste die in een Java lang kan vertegenwoordigen. Dus de volgende methode zal een factoriële (n) berekenen of een illegaalargument-uitzondering gooien als n te groot is.

public long factorial(int n) {
    if (n > 20) throw new IllegalArgumentException(n + " is out of range");
    return (1 > n) ? 1 : n * factorial(n - 1);
}

Nog een (koelere) manier om hetzelfde spul te doen, is om Java 8’s Stream-bibliotheek als volgt te gebruiken:

public long factorial(int n) {
    if (n > 20) throw new IllegalArgumentException(n + " is out of range");        
    return LongStream.rangeClosed(1, n).reduce(1, (a, b) -> a * b);
}

Lees meer over factorials met behulp van Java 8’s beken


Antwoord 9, Autoriteit 23%

Apache Commons Math Package heeft Een factoriale methode , ik denk dat u dat zou kunnen gebruiken.


Antwoord 10, Autoriteit 23%

Kort antwoord is: gebruik de recursie.

U kunt één methode maken en die methode rechtsbinnen bellen binnen dezelfde methode recursief:

public class factorial {
    public static void main(String[] args) {
        System.out.println(calc(10));
    }
    public static long calc(long n) {
        if (n <= 1)
            return 1;
        else
            return n * calc(n - 1);
    }
}

Antwoord 11, Autoriteit 12%

Probeer dit

public static BigInteger factorial(int value){
    if(value < 0){
        throw new IllegalArgumentException("Value must be positive");
    }
    BigInteger result = BigInteger.ONE;
    for (int i = 2; i <= value; i++) {
        result = result.multiply(BigInteger.valueOf(i));
    }
    return result;
}

Antwoord 12, Autoriteit 8%

Ik vond een geweldige truc om factorials te vinden in slechts de helft van de feitelijke vermenigvuldigingen.

Wees geduldig omdat dit een beetje een lange post is.

voor even nummers:
Om de vermenigvuldiging met even getallen te halveren, krijg je n/2 factoren. De eerste factor is het getal waarvan je de faculteit neemt, en de volgende is dat getal plus dat getal min twee. Het volgende nummer is het vorige nummer plus het laatst toegevoegde nummer minus twee. Je bent klaar als het laatste nummer dat je hebt toegevoegd twee was (d.w.z. 2). Dat was waarschijnlijk niet zo logisch, dus laat me je een voorbeeld geven.

8! = 8 * (8 + 6 = 14) * (14 + 4 = 18) * (18 + 2 = 20)
8! = 8 * 14 * 18 * 20 which is **40320** 

Merk op dat ik begon met 8, daarna was het eerste getal dat ik toevoegde 6, dan 4, dan 2, waarbij elk toegevoegd getal twee minder was dan het getal ervoor. Deze methode is gelijk aan het vermenigvuldigen van de minste getallen met de grootste getallen, alleen met minder vermenigvuldiging, zoals:

8! = 1 * 2 * 3 * 4 * 5 * 6 * 7 * 
8! = (1 * 8) * (2 * 7) * (3 * 6) * (4 * 5)
8! = 8 * 14 * 18 * 20

Eenvoudig is het niet 🙂

Nu voor oneven getallen:als het getal oneven is, is het optellen hetzelfde, zoals je elke keer twee aftrekt, maar je stopt bij drie. Het aantal factoren verandert echter. Als je het getal door twee deelt, krijg je een getal dat eindigt op 0,5. De reden is dat als we de uiteinden met elkaar vermenigvuldigen, we het middelste getal overhouden. In principe kan dit allemaal worden opgelost door een aantal factoren op te lossen dat gelijk is aan het aantal gedeeld door twee, afgerond naar boven. Dit was waarschijnlijk ook niet logisch voor mensen zonder wiskundige achtergrond, dus laat me een voorbeeld geven:

9! = 9 * (9 + 7 = 16) * (16 + 5 = 21) * (21 + 3 = 24) * (roundUp(9/2) = 5)
9! = 9 * 16 * 21 * 24 * 5 = **362880**

Opmerking:Als je deze methode niet leuk vindt, kun je ook gewoon de faculteit van het even getal nemen voor de oneven (acht in dit geval) en dit vermenigvuldigen met het oneven getal (bijv. 9! = 8! * 9).

Laten we het nu in Java implementeren:

public static int getFactorial(int num)
{
    int factorial=1;
    int diffrennceFromActualNum=0;
    int previousSum=num;
    if(num==0) //Returning  1 as factorial if number is 0 
        return 1;
    if(num%2==0)//  Checking if Number is odd or even
    { 
        while(num-diffrennceFromActualNum>=2)
        {
            if(!isFirst)
            {
                previousSum=previousSum+(num-diffrennceFromActualNum);  
            }
            isFirst=false;
            factorial*=previousSum;
            diffrennceFromActualNum+=2;
        }
    }
    else // In Odd Case (Number * getFactorial(Number-1))
    {
        factorial=num*getFactorial(num-1);
    }
    return factorial;
}

isFirstis een booleaanse variabele die als statisch is gedeclareerd; het wordt gebruikt voor het eerste geval waarin we de vorige som niet willen veranderen.

Probeer zowel met even als met oneven getallen.


Antwoord 13, autoriteit 8%

Je kunt recursie gebruiken.

public static int factorial(int n){    
      if (n == 0)    
        return 1;    
      else    
        return(n * factorial(n-1));    
     }

en dan nadat u de methode (functie) hierboven hebt gemaakt:

System.out.println(factorial(number of your choice));  
    //direct example
    System.out.println(factorial(3));

Antwoord 14, autoriteit 4%

Het enige zakelijke gebruik van een faculteit dat ik kan bedenken, zijn de Erlang B- en Erlang C-formules, en niet iedereen werkt in een callcenter of voor het telefoonbedrijf. Het nut van een functie voor bedrijven lijkt vaak te dicteren wat er in een taal wordt weergegeven – kijk naar alle gegevensverwerking, XML en webfuncties in de belangrijkste talen.

Het is gemakkelijk om een faculteitsfragment of bibliotheekfunctie voor zoiets in de buurt te houden.


Antwoord 15, autoriteit 4%

Een zeer eenvoudige methode om faculteiten te berekenen:

private double FACT(double n) {
    double num = n;
    double total = 1;
    if(num != 0 | num != 1){
        total = num;
    }else if(num == 1 | num == 0){
        total = 1;
    }
    double num2;
    while(num > 1){
        num2 = num - 1;
        total = total * num2;
        num = num - 1;
    }
    return total;
}

Ik heb dubbel gebruikt omdat ze enorme getallen kunnen bevatten, maar je kunt elk ander type gebruiken, zoals int, long, float, enz.

P.S. Dit is misschien niet de beste oplossing, maar ik ben nieuw in coderen en het kostte me eeuwen om een eenvoudige code te vinden die faculteiten kon berekenen, dus ik moest de methode zelf schrijven, maar ik plaats dit hier zodat het andere mensen zoals ik helpt.


Antwoord 16, autoriteit 4%

U kunt ook de recursieversie gebruiken.

static int myFactorial(int i) {
    if(i == 1)
        return;
    else
        System.out.prinln(i * (myFactorial(--i)));
}

Recursie is meestal minder efficiënt omdat recursies moeten worden gepusht en gepopt, dus iteratie is sneller. Aan de andere kant gebruiken recursieve versies minder of geen lokale variabelen, wat een voordeel is.


Antwoord 17, autoriteit 4%

Factorial is een sterk toenemende discrete functie. Dus ik denk dat het gebruik van BigInteger beter is dan het gebruik van int.
Ik heb de volgende code geïmplementeerd voor het berekenen van de faculteit van niet-negatieve gehele getallen. Ik heb recursie gebruikt in plaats van een lus te gebruiken.

public  BigInteger factorial(BigInteger x){     
    if(x.compareTo(new BigInteger("1"))==0||x.compareTo(new BigInteger("0"))==0)
        return new BigInteger("1");
    else return x.multiply(factorial(x.subtract(new BigInteger("1")))); 
}

Hier is het bereik van een groot geheel getal

-2^Integer.MAX_VALUE (exclusive) to +2^Integer.MAX_VALUE,
where Integer.MAX_VALUE=2^31.

Het bereik van de bovenstaande factoriële methode kan echter tot twee keer worden uitgebreid door niet-ondertekende BigInteger te gebruiken.


Antwoord 18, autoriteit 4%

We hebben een enkele regel om het te berekenen:

Long factorialNumber = LongStream.rangeClosed(2, N).reduce(1, Math::multiplyExact);

Antwoord 19, autoriteit 4%

Een vrij eenvoudige methode

   for ( int i = 1; i < n ; i++ )
    {
            answer = answer * i;
    }

Antwoord 20, autoriteit 4%

   /**
import java liberary class
*/
import java.util.Scanner;
/* class to find factorial of a number
*/
public class factorial
{
public static void main(String[] args)
{
// scanner method for read keayboard values
    Scanner factor= new Scanner(System.in);
    int n;
    double total = 1;
    double sum= 1;
    System.out.println("\nPlease enter an integer: ");
    n = factor.nextInt();
// evaluvate the integer is greater than zero and calculate factorial
if(n==0)
{
    System.out.println(" Factorial of 0 is 1");
}
else if (n>0)
{
    System.out.println("\nThe factorial of " + n + " is " );
    System.out.print(n);
    for(int i=1;i<n;i++)
    {
        do // do while loop for display each integer in the factorial
              {
                System.out.print("*"+(n-i) );
              }
        while ( n == 1);
      total = total * i;
    }
// calculate factorial
sum= total * n;
// display sum of factorial
    System.out.println("\n\nThe "+ n +" Factorial is : "+" "+ sum);
}
// display invalid entry, if enter a value less than zero
else
{
    System.out.println("\nInvalid entry!!");
}System.exit(0);
}
}

Antwoord 21

public static int fact(int i){
    if(i==0)
       return 0;
    if(i>1){
       i = i * fact(--i);
    }
   return i;
}

Antwoord 22

We moeten iteratief implementeren. Als we recursief implementeren, veroorzaakt dit StackOverflow als de invoer erg groot wordt (d.w.z. 2 miljard). En we moeten een ongebonden groottenummer gebruiken, zoals BigInteger om een rekenkundige overloop te voorkomen wanneer een faculteitsgetal groter wordt dan het maximumaantal van een bepaald type (d.w.z. 2 miljard voor int). U kunt int gebruiken voor maximaal 14 faculteit en lang voor maximaal 20
van faculteit voor de overloop.

public BigInteger getFactorialIteratively(BigInteger input) {
    if (input.compareTo(BigInteger.ZERO) <= 0) {
        throw new IllegalArgumentException("zero or negatives are not allowed");
    }
    BigInteger result = BigInteger.ONE;
    for (BigInteger i = BigInteger.ONE; i.compareTo(input) <= 0; i = i.add(BigInteger.ONE)) {
        result = result.multiply(i);
    }
    return result;
}

Als u BigInteger niet kunt gebruiken, voegt u een foutopdracht toe.

public long getFactorialIteratively(long input) {
    if (input <= 0) {
        throw new IllegalArgumentException("zero or negatives are not allowed");
    } else if (input == 1) {
        return 1;
    }
    long prev = 1;
    long result = 0;
    for (long i = 2; i <= input; i++) {
        result = prev * i;
        if (result / prev != i) { // check if result holds the definition of factorial
            // arithmatic overflow, error out
            throw new RuntimeException("value "+i+" is too big to calculate a factorial, prev:"+prev+", current:"+result);
        }
        prev = result;
    }
    return result;
}

Antwoord 23

public int factorial(int num) {
        if (num == 1) return 1;
        return num * factorial(num - 1);
}

Antwoord 24

While lus (voor kleine cijfers)

public class factorial {
public static void main(String[] args) {
    int counter=1, sum=1;
    while (counter<=10) {
        sum=sum*counter;
        counter++;
   }
    System.out.println("Factorial of 10 is " +sum);
   }
}

Antwoord 25

Ik heb dit van EDX gebruikt! het wordt recursie genoemd

  public static int factorial(int n) {
    if (n == 1) {
        return 1;
    } else {
        return n * factorial(n-1);
    }
}

Antwoord 26

met recursie:

public static int factorial(int n)
{
    if(n == 1)
    {
        return 1;
    }               
    return n * factorial(n-1);
}

met while-lus:

public static int factorial1(int n)
{
    int fact=1;
    while(n>=1)
    {
        fact=fact*n;
        n--;
    }
    return fact;
}

Antwoord 27

recursie gebruiken is de eenvoudigste methode. als we de faculteit van willen vinden
N, we moeten rekening houden met de twee gevallen waarin N = 1 en N>1 aangezien in faculteit
we blijven N,N-1, N-2,,,,, vermenigvuldigen tot 1. als we naar N= 0 gaan, krijgen we 0
voor het antwoord. om te voorkomen dat de faculteit nul bereikt, het volgende:
recursieve methode wordt gebruikt. Binnen de faculteitsfunctie, terwijl N>1, de return
waarde wordt vermenigvuldigd met een andere initiatie van de faculteitsfunctie. dit
zal de code recursief de faculteit() aanroepen totdat het de . bereikt
N=1. voor het geval N=1 geeft het N(=1) zelf terug en alle eerder gebouwde
up resultaat van vermenigvuldigd rendement N s wordt vermenigvuldigd met N=1. Zo geeft de
resultaat van de faculteit.

static int factorial(int N) {
    if(N > 1) { 
    return n * factorial(N - 1);
    }
    // Base Case N = 1
    else { 
    return N;
    }

Antwoord 28


public static long factorial(int number) {
    if (number < 0) {
        throw new ArithmeticException(number + " is negative");
    }
    long fact = 1;
    for (int i = 1; i <= number; ++i) {
        fact *= i;
    }
    return fact;
}

recursie gebruiken.


public static long factorial(int number) {
    if (number < 0) {
        throw new ArithmeticException(number + " is negative");
    }
    return number == 0 || number == 1 ? 1 : number * factorial(number - 1);
}

bron


Antwoord 29

Gebruik JAVA 9+, u kunt deze oplossing gebruiken. Dit gebruikt Biginteger, ideaal voor het vasthouden van grote aantallen.

...    
import java.math.BigInteger;
import java.util.stream.Stream;
...
String getFactorial(int n) {
    return Stream.iterate(BigInteger.ONE, i -> i.add(BigInteger.ONE)).parallel() 
            .limit(n).reduce(BigInteger.ONE, BigInteger::multiply).toString();
}

ANTWOORD 30

met behulp van dynamische programmering is efficiënt

Als u het wilt gebruiken om opnieuw en opnieuw (zoals caching)

te berekenen

Java Code:

int fact[]=new int[n+1]; //n is the required number you want to find factorial for.
int factorial(int num)
 {
    if(num==0){
     fact[num]=1;
     return fact[num];
       }
     else
       fact[num]=(num)*factorial(num-1);
     return fact[num];
 }

Other episodes