As we all know, the simplest algorithm to generate Fibonacci sequence is as follows:
if(n<=0) return 0;
else if(n==1) return 1;
f(n) = f(n-1) + f(n-2);
But this algorithm has some repetitive calculation. For example, if you calculate f(5), it will calculate f(4) and f(3). When you calculate f(4), it will again calculate both f(3) and f(2). Could someone give me a more time-efficient recursive algorithm?
I have read about some of the methods for calculating Fibonacci with efficient time complexity following are some of them -
Method 1 - Dynamic Programming
Now here the substructure is commonly known hence I'll straightly Jump to the solution -
static int fib(int n)
{
int f[] = new int[n+2]; // 1 extra to handle case, n = 0
int i;
f[0] = 0;
f[1] = 1;
for (i = 2; i <= n; i++)
{
f[i] = f[i-1] + f[i-2];
}
return f[n];
}
A space-optimized version of above can be done as follows -
static int fib(int n)
{
int a = 0, b = 1, c;
if (n == 0)
return a;
for (int i = 2; i <= n; i++)
{
c = a + b;
a = b;
b = c;
}
return b;
}
Method 2- ( Using power of the matrix {{1,1},{1,0}} )
This an O(n) which relies on the fact that if we n times multiply the matrix M = {{1,1},{1,0}} to itself (in other words calculate power(M, n )), then we get the (n+1)th Fibonacci number as the element at row and column (0, 0) in the resultant matrix. This solution would have O(n) time.
The matrix representation gives the following closed expression for the Fibonacci numbers:
fibonaccimatrix
static int fib(int n)
{
int F[][] = new int[][]{{1,1},{1,0}};
if (n == 0)
return 0;
power(F, n-1);
return F[0][0];
}
/*multiplies 2 matrices F and M of size 2*2, and
puts the multiplication result back to F[][] */
static void multiply(int F[][], int M[][])
{
int x = F[0][0]*M[0][0] + F[0][1]*M[1][0];
int y = F[0][0]*M[0][1] + F[0][1]*M[1][1];
int z = F[1][0]*M[0][0] + F[1][1]*M[1][0];
int w = F[1][0]*M[0][1] + F[1][1]*M[1][1];
F[0][0] = x;
F[0][1] = y;
F[1][0] = z;
F[1][1] = w;
}
/*function that calculates F[][] raise to the power n and puts the
result in F[][]*/
static void power(int F[][], int n)
{
int i;
int M[][] = new int[][]{{1,1},{1,0}};
// n - 1 times multiply the matrix to {{1,0},{0,1}}
for (i = 2; i <= n; i++)
multiply(F, M);
}
This can be optimized to work in O(Logn) time complexity. We can do recursive multiplication to get power(M, n) in the previous method.
static int fib(int n)
{
int F[][] = new int[][]{{1,1},{1,0}};
if (n == 0)
return 0;
power(F, n-1);
return F[0][0];
}
static void multiply(int F[][], int M[][])
{
int x = F[0][0]*M[0][0] + F[0][1]*M[1][0];
int y = F[0][0]*M[0][1] + F[0][1]*M[1][1];
int z = F[1][0]*M[0][0] + F[1][1]*M[1][0];
int w = F[1][0]*M[0][1] + F[1][1]*M[1][1];
F[0][0] = x;
F[0][1] = y;
F[1][0] = z;
F[1][1] = w;
}
static void power(int F[][], int n)
{
if( n == 0 || n == 1)
return;
int M[][] = new int[][]{{1,1},{1,0}};
power(F, n/2);
multiply(F, F);
if (n%2 != 0)
multiply(F, M);
}
Method 3 (O(log n) Time)
Below is one more interesting recurrence formula that can be used to find nth Fibonacci Number in O(log n) time.
If n is even then k = n/2:
F(n) = [2*F(k-1) + F(k)]*F(k)
If n is odd then k = (n + 1)/2
F(n) = F(k)*F(k) + F(k-1)*F(k-1)
How does this formula work?
The formula can be derived from the above matrix equation.
fibonaccimatrix
Taking determinant on both sides, we get
(-1)n = Fn+1Fn-1 – Fn2
Moreover, since AnAm = An+m for any square matrix A, the following identities can be derived (they are obtained from two different coefficients of the matrix product)
FmFn + Fm-1Fn-1 = Fm+n-1
By putting n = n+1,
FmFn+1 + Fm-1Fn = Fm+n
Putting m = n
F2n-1 = Fn2 + Fn-12
F2n = (Fn-1 + Fn+1)Fn = (2Fn-1 + Fn)Fn (Source: Wiki)
To get the formula to be proved, we simply need to do the following
If n is even, we can put k = n/2
If n is odd, we can put k = (n+1)/2
public static int fib(int n)
{
if (n == 0)
return 0;
if (n == 1 || n == 2)
return (f[n] = 1);
// If fib(n) is already computed
if (f[n] != 0)
return f[n];
int k = (n & 1) == 1? (n + 1) / 2
: n / 2;
// Applyting above formula [See value
// n&1 is 1 if n is odd, else 0.
f[n] = (n & 1) == 1? (fib(k) * fib(k) +
fib(k - 1) * fib(k - 1))
: (2 * fib(k - 1) + fib(k))
* fib(k);
return f[n];
}
Method 4 - Using a formula
In this method, we directly implement the formula for the nth term in the Fibonacci series. Time O(1) Space O(1)
Fn = {[(√5 + 1)/2] ^ n} / √5
static int fib(int n) {
double phi = (1 + Math.sqrt(5)) / 2;
return (int) Math.round(Math.pow(phi, n)
/ Math.sqrt(5));
}
Reference: http://www.maths.surrey.ac.uk/hosted-sites/R.Knott/Fibonacci/fibFormula.html
Look here for implementation in Erlang which uses formula
. It shows nice linear resulting behavior because in O(M(n) log n) part M(n) is exponential for big numbers. It calculates fib of one million in 2s where result has 208988 digits. The trick is that you can compute exponentiation in O(log n) multiplications using (tail) recursive formula (tail means with O(1) space when used proper compiler or rewrite to cycle):
% compute X^N
power(X, N) when is_integer(N), N >= 0 ->
power(N, X, 1).
power(0, _, Acc) ->
Acc;
power(N, X, Acc) ->
if N rem 2 =:= 1 ->
power(N - 1, X, Acc * X);
true ->
power(N div 2, X * X, Acc)
end.
where X and Acc you substitute with matrices. X will be initiated with and Acc with identity I equals to .
One simple way is to calculate it iteratively instead of recursively. This will calculate F(n) in linear time.
def fib(n):
a,b = 0,1
for i in range(n):
a,b = a+b,a
return a
Hint: One way you achieve faster results is by using Binet's formula:
Here is a way of doing it in Python:
from decimal import *
def fib(n):
return int((Decimal(1.6180339)**Decimal(n)-Decimal(-0.6180339)**Decimal(n))/Decimal(2.236067977))
you can save your results and use them :
public static long[] fibs;
public long fib(int n) {
fibs = new long[n];
return internalFib(n);
}
public long internalFib(int n) {
if (n<=2) return 1;
fibs[n-1] = fibs[n-1]==0 ? internalFib(n-1) : fibs[n-1];
fibs[n-2] = fibs[n-2]==0 ? internalFib(n-2) : fibs[n-2];
return fibs[n-1]+fibs[n-2];
}
F(n) = (φ^n)/√5 and round to nearest integer, where φ is the golden ratio....
φ^n can be calculated in O(lg(n)) time hence F(n) can be calculated in O(lg(n)) time.
// D Programming Language
void vFibonacci ( const ulong X, const ulong Y, const int Limit ) {
// Equivalent : if ( Limit != 10 ). Former ( Limit ^ 0xA ) is More Efficient However.
if ( Limit ^ 0xA ) {
write ( Y, " " ) ;
vFibonacci ( Y, Y + X, Limit + 1 ) ;
} ;
} ;
// Call As
// By Default the Limit is 10 Numbers
vFibonacci ( 0, 1, 0 ) ;
EDIT: I actually think Hynek Vychodil's answer is superior to mine, but I'm leaving this here just in case someone is looking for an alternate method.
I think the other methods are all valid, but not optimal. Using Binet's formula should give you the right answer in principle, but rounding to the closest integer will give some problems for large values of n. The other solutions will unnecessarily recalculate the values upto n every time you call the function, and so the function is not optimized for repeated calling.
In my opinion the best thing to do is to define a global array and then to add new values to the array IF needed. In Python:
import numpy
fibo=numpy.array([1,1])
last_index=fibo.size
def fib(n):
global fibo,last_index
if (n>0):
if(n>last_index):
for i in range(last_index+1,n+1):
fibo=numpy.concatenate((fibo,numpy.array([fibo[i-2]+fibo[i-3]])))
last_index=fibo.size
return fibo[n-1]
else:
print "fib called for index less than 1"
quit()
Naturally, if you need to call fib for n>80 (approximately) then you will need to implement arbitrary precision integers, which is easy to do in python.
This will execute faster, O(n)
def fibo(n):
a, b = 0, 1
for i in range(n):
if i == 0:
print(i)
elif i == 1:
print(i)
else:
temp = a
a = b
b += temp
print(b)
n = int(input())
fibo(n)
Related
I would like to generate in an efficient way a list of integers (preferably ordered)
with the following defining properties:
All integers have the same number of bit set N.
All integers have the same sum of bit indices K.
To be definite, for an integer I
its binary representation is:
$I=\sum_{j=0}^M c_j 2^j$ where $c_j=0$ or $1$
The number of bit sets is:
$N(I)=\sum_{j=0}^M c_j$
The sum of bit indices is:
$K(I)=\sum_{j=0}^M j c_j$
I have an inefficient way to generate the list as follows:
make a do/for loop over integers incrementing by use
of a "snoob" function - smallest next integer with same number of bit set
and at each increment checking if it has the correct value of K
this is grossly inefficient because in general starting from an integer
with the correct N and K value the snoob integer from I does not have the correct K and one has to make many snoob calculations to get the next integer
with both N and K equal to the chosen values.
Using snoob gives an ordered list which is handy for dichotomic search but
not absolutely compulsory.
Counting the number of elements in this list is easily done by recursion
when viewed as a partition numner counting. here is a recursive function in fortran 90 doing that job:
=======================================================================
recursive function BoundedPartitionNumberQ(N, M, D) result (res)
implicit none
! number of partitions of N into M distinct integers, bounded by D
! appropriate for Fermi counting rules
integer(8) :: N, M, D, Nmin
integer(8) :: res
Nmin = M*(M+1)/2 ! the Fermi sea
if(N < Nmin) then
res = 0
else if((N == Nmin) .and. (D >= M)) then
res = 1
else if(D < M) then
res = 0
else if(D == M) then
if(N == Nmin) then
res = 1
else
res = 0
endif
else if(M == 0) then
res = 0
else
res = BoundedPartitionNumberQ(N-M,M-1,D-1)+BoundedPartitionNumberQ(N-M,M,D-1)
endif
end function BoundedPartitionNumberQ
========================================================================================
My present solution is inefficient when I want to generate lists with several $10^7$
elements. Ultimately I want to stay within the realm of C/C++/Fortran and reach lists of lengths
up to a few $10^9$
my present f90 code is the following:
program test
implicit none
integer(8) :: Nparticles
integer(8) :: Nmax, TmpL, CheckL, Nphi
integer(8) :: i, k, counter
integer(8) :: NextOne
Nphi = 31 ! word size is Nphi+1
Nparticles = 16 ! number of bit set
print*,Nparticles,Nphi
Nmax = ishft(1_8, Nphi + 1) - ishft(1_8, Nphi + 1 - Nparticles)
i = ishft(1, Nparticles) - 1
counter = 0
! integer CheckL is the sum of bit indices
CheckL = Nparticles*Nphi/2 ! the value of the sum giving the largest list
do while(i .le. Nmax) ! we increment the integer
TmpL = 0
do k=0,Nphi
if (btest(i,k)) TmpL = TmpL + k
end do
if (TmpL == CheckL) then ! we check whether the sum of bit indices is OK
counter = counter + 1
end if
i = NextOne(i) ! a version of "snoob" described below
end do
print*,counter
end program
!==========================================================================
function NextOne (state)
implicit none
integer(8) :: bit
integer(8) :: counter
integer(8) :: NextOne,state,pstate
bit = 1
counter = -1
! find first one bit
do while (iand(bit,state) == 0)
bit = ishft(bit,1)
end do
! find next zero bit
do while (iand(bit,state) /= 0)
counter = counter + 1
bit = ishft(bit,1)
end do
if (bit == 0) then
print*,'overflow in NextOne'
NextOne = not(0)
else
state = iand(state,not(bit-1)) ! clear lower bits i &= (~(bit-1));
pstate = ishft(1_8,counter)-1 ! needed by IBM/Zahir compiler
! state = ior(state,ior(bit,ishft(1,counter)-1)) ! short version OK with gcc
state = ior(state,ior(bit,pstate))
NextOne = state
end if
end function NextOne
Since you mentioned C/C++/Fortran, I've tried to keep this relatively language agnostic/easily transferable but have also included faster builtins alternatives where applicable.
All integers have the same number of bit set N
Then we can also say, all valid integers will be permutations of N set bits.
First, we must generate the initial/min permutation:
uint32_t firstPermutation(uint32_t n){
// Fill the first n bits (on the right)
return (1 << n) -1;
}
Next, we must set the final/max permutation - indicating the 'stop point':
uint32_t lastPermutation(uint32_t n){
// Fill the last n bits (on the left)
return (0xFFFFFFFF >> n) ^ 0xFFFFFFFF;
}
Finally, we need a way to get the next permutation.
uint32_t nextPermutation(uint32_t n){
uint32_t t = (n | (n - 1)) + 1;
return t | ((((t & -t) / (n & -n)) >> 1) - 1);
}
// or with builtins:
uint32_t nextPermutation(uint32_t &p){
uint32_t t = (p | (p - 1));
return (t + 1) | (((~t & -~t) - 1) >> (__builtin_ctz(p) + 1));
}
All integers have the same sum of bit indices K
Assuming these are integers (32bit), you can use this DeBruijn sequence to quickly identify the index of the first set bit - fsb.
Similar sequences exist for other types/bitcounts, for example this one could be adapted for use.
By stripping the current fsb, we can apply the aforementioned technique to identify index of the next fsb, and so on.
int sumIndices(uint32_t n){
const int MultiplyDeBruijnBitPosition[32] = {
0, 1, 28, 2, 29, 14, 24, 3, 30, 22, 20, 15, 25, 17, 4, 8,
31, 27, 13, 23, 21, 19, 16, 7, 26, 12, 18, 6, 11, 5, 10, 9
};
int sum = 0;
// Get fsb idx
do sum += MultiplyDeBruijnBitPosition[((uint32_t)((n & -n) * 0x077CB531U)) >> 27];
// strip fsb
while (n &= n-1);
return sum;
}
// or with builtin
int sumIndices(uint32_t n){
int sum = 0;
do sum += __builtin_ctz(n);
while (n &= n-1);
return sum;
}
Finally, we can iterate over each permutation, checking if the sum of all indices matches the specified K value.
p = firstPermutation(n);
lp = lastPermutation(n);
do {
p = nextPermutation(p);
if (sumIndices(p) == k){
std::cout << "p:" << p << std::endl;
}
} while(p != lp);
You could easily change the 'handler' code to do something similar starting at a given integer - using it's N & K values.
A basic recursive implementation could be:
void listIntegersWithWeight(int currentBitCount, int currentWeight, uint32_t pattern, int index, int n, int k, std::vector<uint32_t> &res)
{
if (currentBitCount > n ||
currentWeight > k)
return;
if (index < 0)
{
if (currentBitCount == n && currentWeight == k)
res.push_back(pattern);
}
else
{
listIntegersWithWeight(currentBitCount, currentWeight, pattern, index - 1, n, k, res);
listIntegersWithWeight(currentBitCount + 1, currentWeight + index, pattern | (1u << index), index - 1, n, k, res);
}
}
That is not my suggestion, just the starting point. On my PC, for n = 16, k = 248, both this version and the iterative version take almost (but not quite) 9 seconds. Almost exactly the same amount of time, but that's just a coincidence. More pruning can be done:
currentBitCount + index + 1 < n if the number of set bits cannot reach n with the number of unfilled positions that are left, continuing is pointless.
currentWeight + (index * (index + 1) / 2) < k if the sum of positions cannot reach k, continuing is pointless.
Together:
void listIntegersWithWeight(int currentBitCount, int currentWeight, uint32_t pattern, int index, int n, int k, std::vector<uint32_t> &res)
{
if (currentBitCount > n ||
currentWeight > k ||
currentBitCount + index + 1 < n ||
currentWeight + (index * (index + 1) / 2) < k)
return;
if (index < 0)
{
if (currentBitCount == n && currentWeight == k)
res.push_back(pattern);
}
else
{
listIntegersWithWeight(currentBitCount, currentWeight, pattern, index - 1, n, k, res);
listIntegersWithWeight(currentBitCount + 1, currentWeight + index, pattern | (1u << index), index - 1, n, k, res);
}
}
On my PC with the same parameters, this only takes half a second. It can probably be improved further.
I need to do it with recursion, but the problem is that function depends on only ONE parameter and inside function it depends on two ( k and n ), also how to find minimum value if it returns only one value?
The function is :
I've already tried to make random k, but I don't think that is really good idea.
F1(int n) {
Random random = new Random();
int k = random.Next(1,10);
if (1 <= k && k <= n){
return Math.Min(F1(k - 1) + F1(n - k) + n);
} else {
return 0;
}
}
You need to make a loop traversing all k values in range 1..n. Something like this:
F1(int n) {
if (n == 0)
return ???? what is starting value?
minn = F1(0) + F1(n - 1) + n
for (int k = 2; k <= n; k++)
minn = Math.Min(minn, F1(k - 1) + F1(n - k) + n);
return minn;
}
for example, why don't we do n/3 instead of n/2
Some Maths
The recurrence relation for a binary search using n/2 is
T(n) = T(n/2) + C
which can be simplified to
log2(m) = n
and n/3
T(n) = T(n/3) + C
which can be simplified to
log3(m) = n
so my question is: since log3(m) < log2(m) why do we use n/2
It is true that Ternary search has fewer recursive calls than Binary search (log3(m) < log2(m)) however Ternary search has more comparisons in the worst case than Binary search.
To examine a bit more let's compare Binary and Ternary search algorithms in C++
Binary Search
// A recursive binary search function. It returns location of x in
// given array arr[l..r] is present, otherwise -1
int binarySearch(int arr[], int l, int r, int x)
{
if (r >= l)
{
int mid = l + (r - l)/2;
// If the element is present at the middle itself
if (arr[mid] == x) return mid;
// If element is smaller than mid, then it can only be present
// in left subarray
if (arr[mid] > x) return binarySearch(arr, l, mid-1, x);
// Else the element can only be present in right subarray
return binarySearch(arr, mid+1, r, x);
}
// We reach here when element is not present in array
return -1;
}
Ternary Search
// A recursive ternary search function. It returns location of x in
// given array arr[l..r] is present, otherwise -1
int ternarySearch(int arr[], int l, int r, int x)
{
if (r >= l)
{
int mid1 = l + (r - l)/3;
int mid2 = mid1 + (r - l)/3;
// If x is present at the mid1
if (arr[mid1] == x) return mid1;
// If x is present at the mid2
if (arr[mid2] == x) return mid2;
// If x is present in left one-third
if (arr[mid1] > x) return ternarySearch(arr, l, mid1-1, x);
// If x is present in right one-third
if (arr[mid2] < x) return ternarySearch(arr, mid2+1, r, x);
// If x is present in middle one-third
return ternarySearch(arr, mid1+1, mid2-1, x);
}
// We reach here when element is not present in array
return -1;
}
In the worst case, Binary search does 2log2(n) + 1 comparisons where Ternary search does 4log3(n) + 1 comparisons
The comparisons boil down to log2(n) and 2log3(n)
Changing bases, 2log3(n) = (2 / log2(3)) * log2(n)
Since (2 / log2(3)) > 1 Ternay search does more comparisons in the worst case
Source
I want to compute sequence of numbers like this:
n*(n-1)+n*(n-1)*(n-2)+n*(n-1)*(n-2)*(n-3)+n*(n-1)*(n-2)*(n-3)*(n-4)+...+n(n-1)...(n-n)
For example n=5 and sum equals 320.
I have a function, which compute one element:
int fac(int n, int s)
{
if (n > s)
return n*fac(n - 1, s);
return 1;
}
Recomputing the factorial for each summand is quite wasteful. Instead, I'd suggest to use memoization. If you reorder
n*(n-1) + n*(n-1)*(n-2) + n*(n-1)*(n-2)*(n-3) + n*(n-1)*(n-2)*(n-3)*...*1
you get
n*(n-1)*(n-2)*(n-3)*...*1 + n*(n-1)*(n-2)*(n-3) + n*(n-1)*(n-2) + n*(n-1)
Notice how you start with the product of 1..n, then you add the product of 1..n divided by 1, then you add the product divided by 1*2 etc.
I think a much more efficient definition of your function is (in Python):
def f(n):
p = product(range(1, n+1))
sum_ = p
for i in range(1, n-1):
p /= i
sum_ += p
return sum_
A recursive version of this definition is:
def f(n):
def go(sum_, i):
if i >= n-1:
return sum_
return sum_ + go(sum_ / i, i+1)
return go(product(range(1, n+1)), 1)
Last but not least, you can also define the function without any explicit recursion by using reduce to generate the list of summands (this is a more 'functional' -- as in functional programming -- style):
def f(n):
summands, _ = reduce(lambda (lst, p), i: (lst + [p], p / i),
range(1, n),
([], product(range(1, n+1))))
return sum(summands)
This style is very concise in functional programming languages such as Haskell; Haskell has a function call scanl which simplifies generating the summands so that the definition is just:
f n = sum $ scanl (/) (product [1..n]) [1..(n-2)]
Something like this?
function fac(int n, int s)
{
if (n >= s)
return n * fac(n - 1, s);
return 1;
}
int sum = 0;
int s = 4;
n = 5;
while(s > 0)
{
sum += fac(n, s);
s--;
}
print sum; //320
Loop-free version:
int fac(int n, int s)
{
if (n >= s)
return n * fac(n - 1, s);
return 1;
}
int compute(int n, int s, int sum = 0)
{
if(s > 0)
return compute(n, s - 1, sum + fac(n, s));
return sum;
}
print compute(5, 4); //320
Ok ther is not mutch to write. I would suggest 2 methodes if you want to solve this recursiv. (Becaus of the recrusiv faculty the complexity is a mess and runtime will increase drasticaly with big numbers!)
int func(int n){
return func(n, 2);
}
int func(int n, int i){
if (i < n){
return n*(fac(n-1,n-i)+func(n, i + 1));
}else return 0;
}
int fac(int i,int a){
if(i>a){
return i*fac(i-1, a);
}else return 1;
}
What is the most efficient way to calculate the least common multiple of two integers?
I just came up with this, but it definitely leaves something to be desired.
int n=7, m=4, n1=n, m1=m;
while( m1 != n1 ){
if( m1 > n1 )
n1 += n;
else
m1 += m;
}
System.out.println( "lcm is " + m1 );
The least common multiple (lcm) of a and b is their product divided by their greatest common divisor (gcd) ( i.e. lcm(a, b) = ab/gcd(a,b)).
So, the question becomes, how to find the gcd? The Euclidean algorithm is generally how the gcd is computed. The direct implementation of the classic algorithm is efficient, but there are variations that take advantage of binary arithmetic to do a little better. See Knuth's "The Art of Computer Programming" Volume 2, "Seminumerical Algorithms" § 4.5.2.
Remember
The least common multiple is the least whole number that is a multiple of each of two or more numbers.
If you are trying to figure out the LCM of three integers, follow these steps:
**Find the LCM of 19, 21, and 42.**
Write the prime factorization for each number. 19 is a prime number. You do not need to factor 19.
21 = 3 × 7
42 = 2 × 3 × 7
19
Repeat each prime factor the greatest number of times it appears in any of the prime factorizations above.
2 × 3 × 7 × 19 = 798
The least common multiple of 21, 42, and 19 is 798.
I think that the approach of "reduction by the greatest common divider" should be faster. Start by calculating the GCD (e.g. using Euclid's algorithm), then divide the product of the two numbers by the GCD.
Best solution in C++ below without overflowing
#include <iostream>
using namespace std;
long long gcd(long long int a, long long int b){
if(b==0)
return a;
return gcd(b,a%b);
}
long long lcm(long long a,long long b){
if(a>b)
return (a/gcd(a,b))*b;
else
return (b/gcd(a,b))*a;
}
int main()
{
long long int a ,b ;
cin>>a>>b;
cout<<lcm(a,b)<<endl;
return 0;
}
First of all, you have to find the greatest common divisor
for(int i=1; i<=a && i<=b; i++) {
if (i % a == 0 && i % b == 0)
{
gcd = i;
}
}
After that, using the GCD you can easily find the least common multiple like this
lcm = a / gcd * b;
I don't know whether it is optimized or not, but probably the easiest one:
public void lcm(int a, int b)
{
if (a > b)
{
min = b;
max = a;
}
else
{
min = a;
max = b;
}
for (i = 1; i < max; i++)
{
if ((min*i)%max == 0)
{
res = min*i;
break;
}
}
Console.Write("{0}", res);
}
Here is a highly efficient approach to find the LCM of two numbers in python.
def gcd(a, b):
if min(a, b) == 0:
return max(a, b)
a_1 = max(a, b) % min(a, b)
return gcd(a_1, min(a, b))
def lcm(a, b):
return (a * b) // gcd(a, b)
Using Euclidean algorithm to find gcd and then calculating the lcm dividing a by the product of gcd and b worked for me.
int euclidgcd(int a, int b){
if(b==0)
return a;
int a_rem = a % b;
return euclidgcd(b, a_rem);
}
long long lcm(int a, int b) {
int gcd=euclidgcd(a, b);
return (a/gcd*b);
}
int main() {
int a, b;
std::cin >> a >> b;
std::cout << lcm(a, b) << std::endl;
return 0;
}
Take successive multiples of the larger of the two numbers until the result is a multiple of the smaller.
this might work..
public int LCM(int x, int y)
{
int larger = x>y? x: y,
smaller = x>y? y: x,
candidate = larger ;
while (candidate % smaller != 0) candidate += larger ;
return candidate;
}
C++ template. Compile time
#include <iostream>
const int lhs = 8, rhs = 12;
template<int n, int mod_lhs=n % lhs, int mod_rhs=n % rhs> struct calc {
calc() { }
};
template<int n> struct calc<n, 0, 0> {
calc() { std::cout << n << std::endl; }
};
template<int n, int mod_rhs> struct calc<n, 0, mod_rhs> {
calc() { }
};
template<int n, int mod_lhs> struct calc <n, mod_lhs, 0> {
calc() { }
};
template<int n> struct lcm {
lcm() {
lcm<n-1>();
calc<n>();
}
};
template<> struct lcm<0> {
lcm() {}
};
int main() {
lcm<lhs * rhs>();
}
Euclidean GCD code snippet
int findGCD(int a, int b) {
if(a < 0 || b < 0)
return -1;
if (a == 0)
return b;
else if (b == 0)
return a;
else
return findGCD(b, a % b);
}
Product of 2 numbers is equal to LCM * GCD or HCF. So best way to find LCM is to find GCD and divide the product with GCD. That is, LCM(a,b) = (a*b)/GCD(a,b).
There is no way more efficient than using a built-in function!
As of Python 3.8 lcm() function has been added in math library. And can be called with folowing signature:
math.lcm(*integers)
Returns the least common multiple of the specified integer arguments. If all arguments are nonzero, then the returned value is the smallest positive integer that is a multiple of all arguments. If any of the arguments is zero, then the returned value is 0. lcm() without arguments returns 1.
Extending #John D. Cook answer that is also marked answer for this question. ( https://stackoverflow.com/a/3154503/13272795), I am sharing algorithm to find LCM of n numbers, it maybe LCM of 2 numbers or any numbers. Source for this code is this
int gcd(int a, int b)
{
if (b == 0)
return a;
return gcd(b, a % b);
}
// Returns LCM of array elements
ll findlcm(int arr[], int n)
{
// Initialize result
ll ans = arr[0];
// ans contains LCM of arr[0], ..arr[i]
// after i'th iteration,
for (int i = 1; i < n; i++)
ans = arr[i] * ans/gcd(arr[i], ans);
return ans;
}
Since we know the mathematic property which states that "product of LCM and HCF of any two numbers is equal to the product of the two numbers".
lets say X and Y are two integers,
then
X * Y = HCF(X, Y) * LCM(X, Y)
Now we can find LCM by knowing the HCF, which we can find through Euclidean Algorithm.
LCM(X, Y) = (X * Y) / HCF(X, Y)
Hope this will be efficient.
import java.util.*;
public class Hello {
public static int HCF(int X, int Y){
if(X == 0)return Y;
return HCF(Y%X, X);
}
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int X = scanner.nextInt(), Y = scanner.nextInt();
System.out.print((X * Y) / HCF(X, Y));
}
}
Yes, there are numerous way to calculate LCM such as using GCD (HCF).
You can apply prime decomposition such as (optimized/naive) Sieve Eratosthenes or find factor of prime number to compute GCD, which is way more faster than calculate LCM directly. Then as all said above, LCM(X, Y) = (X * Y) / GCD(X, Y)
I googled the same question, and found this Stackoverflow page,
however I come up with another simple solution using python
def find_lcm(numbers):
h = max(numbers)
lcm = h
def check(l, numbers):
remainders = [ l%n==0 for n in numbers]
return all(remainders)
while (check(lcm, numbers) == False):
lcm = lcm + h
return lcm
for
numbers = [120,150,135,225]
it will return 5400
numbers = [120,150,135,225]
print(find_lcm(numbers)) # will print 5400