Well, we all know that if N is given it\'s easy to calculate N!. But what about the inverse?
N! is given and you are about to find N - Is that possible ? I\'m curio
X=1
.F=X!
X
is N.X=X+1
, then start again at #2.You can optimize by using the previous result of F
to compute the new F
(new F = new X * old F
).
It's just as fast as going the opposite direction, if not faster, given that division generally takes longer than multiplication. A given factorial A!
is guaranteed to have all integers less than A
as factors in addition to A, so you'd spend just as much time factoring those out as you would just computing a running factorial.
Based on:
Full inverted factorial valid for x>1
Use the suggested calculation. If factorial is expressible in full binary form the algorithm is:
Suppose input is factorial x, x=n!
__uint128_t factorial(int n); int invert_factorial(__uint128_t fact) { if (fact == 1) return 1; int t = __builtin_ffs(fact)-1; int res = fact/factorial(t); return t + (int)log(res)/log(t+1); }
128-bit is giving in on 34!
int p = 1,i;
//assume variable fact_n has the value n!
for(i = 2; p <= fact_n; i++) p = p*i;
//i is the number you are looking for if p == fact_n else fact_n is not a factorial
I know it isn't a pseudocode, but it's pretty easy to understand
If you do not know whether a number M
is N!
or not, a decent test is to test if it's divisible by all the small primes until the Sterling approximation of that prime is larger than M
. Alternatively, if you have a table of factorials but it doesn't go high enough, you can pick the largest factorial in your table and make sure M
is divisible by that.
If you have Q=N! in binary, count the trailing zeros. Call this number J.
If N is 2K or 2K+1, then J is equal to 2K minus the number of 1's in the binary representation of 2K, so add 1 over and over until the number of 1's you have added is equal to the number of 1's in the result.
Now you know 2K, and N is either 2K or 2K+1. To tell which one it is, count the factors of the biggest prime (or any prime, really) in 2K+1, and use that to test Q=(2K+1)!.
For example, suppose Q (in binary) is
1111001110111010100100110000101011001111100000110110000000000000000000
(Sorry it's so small, but I don't have tools handy to manipulate larger numbers.)
There are 19 trailing zeros, which is
10011
Now increment:
1: 10100
2: 10101
3: 10110 bingo!
So N is 22 or 23. I need a prime factor of 23, and, well, I have to pick 23 (it happens that 2K+1 is prime, but I didn't plan that and it isn't needed). So 23^1 should divide 23!, it doesn't divide Q, so
N=22