Count ways to reach the nth stair using step 1, 2 or 3
Last Updated :
12 Dec, 2024
A child is running up a staircase with n steps and can hop either 1 step, 2 steps, or 3 steps at a time. The task is to implement a method to count how many possible ways the child can run up the stairs.
Examples:
Input: 4
Output: 7
Explanation: There are seven ways: {1, 1, 1, 1}, {1, 2, 1}, {2, 1, 1}, {1, 1, 2}, {2, 2}, {3, 1}, {1, 3}.
Input: 3
Output: 4
Explanation: There are four ways: {1, 1, 1}, {1, 2}, {2, 1}, {3}.
Using Recursion - O(3^n) Time and O(n) Space
There are n stairs, and a person is allowed to jump next stair, skip one stair or skip two stairs. So there are n stairs. So if a person is standing at i-th stair, the person can move to i+1, i+2, i+3-th stair. A recursive function can be formed where at current index i the function is recursively called for i+1, i+2 and i+3 th stair.
There is another way of forming the recursive function. To reach a stair i, a person has to jump either from i-1, i-2 or i-3 th stair.
countWays(n) = countWays(n-1) + countWays(n-2) + countWays(n-3)
Below is the implementation of the above approach:
C++
// C++ program to count number of
// ways to reach nth stair.
#include <iostream>
using namespace std;
int countWays(int n) {
// Base case for 0th stair
if (n == 0) return 1;
// For invalid stair, return 0.
if (n < 0) return 0;
// Count number of ways to reach (n-1), (n-2),
// (n-3) stair
return countWays(n - 1) + countWays(n - 2) + countWays(n - 3);
}
int main() {
int n = 4;
cout << countWays(n) << endl;
return 0;
}
C
// C program to count number of
// ways to reach nth stair.
#include <stdio.h>
int countWays(int n) {
// Base case for 0th stair
if (n == 0) return 1;
// For invalid stair, return 0.
if (n < 0) return 0;
// Count number of ways to reach (n-1), (n-2),
// (n-3) stair
return countWays(n - 1) + countWays(n - 2) + countWays(n - 3);
}
int main() {
int n = 4;
printf("%d\n", countWays(n));
return 0;
}
Java
// Java program to count number of
// ways to reach nth stair.
class GfG {
static int countWays(int n) {
// Base case for 0th stair
if (n == 0) return 1;
// For invalid stair, return 0.
if (n < 0) return 0;
// Count number of ways to reach (n-1), (n-2),
// (n-3) stair
return countWays(n - 1) + countWays(n - 2) + countWays(n - 3);
}
public static void main(String[] args) {
int n = 4;
System.out.println(countWays(n));
}
}
Python
# Python program to count number of
# ways to reach nth stair.
def countWays(n):
# Base case for 0th stair
if n == 0:
return 1
# For invalid stair, return 0.
if n < 0:
return 0
# Count number of ways to reach (n-1), (n-2),
# (n-3) stair
return countWays(n - 1) + countWays(n - 2) + countWays(n - 3)
if __name__ == "__main__":
n = 4
print(countWays(n))
C#
// C# program to count number of
// ways to reach nth stair.
using System;
class GfG {
static int countWays(int n) {
// Base case for 0th stair
if (n == 0) return 1;
// For invalid stair, return 0.
if (n < 0) return 0;
// Count number of ways to reach (n-1), (n-2),
// (n-3) stair
return countWays(n - 1) + countWays(n - 2) + countWays(n - 3);
}
static void Main(string[] args) {
int n = 4;
Console.WriteLine(countWays(n));
}
}
JavaScript
// JavaScript program to count number of
// ways to reach nth stair.
function countWays(n) {
// Base case for 0th stair
if (n === 0) return 1;
// For invalid stair, return 0.
if (n < 0) return 0;
// Count number of ways to reach (n-1), (n-2),
// (n-3) stair
return countWays(n - 1) + countWays(n - 2) + countWays(n - 3);
}
const n = 4;
console.log(countWays(n));
Using Top-Down DP (Memoization) - O(n) Time and O(n) Space
If we notice carefully, we can observe that the above recursive solution holds the following two properties of Dynamic Programming:
1. Optimal Substructure:
Number of ways to reach the nth stair, i.e., countWays(n), depends on the optimal solutions of the subproblems countWays(n-1) , countWays(n-2) and countWays(n-3). By combining these optimal substructures, we can efficiently calculate the total number of ways to reach the nth stair.
2. Overlapping Subproblems:
While applying a recursive approach in this problem, we notice that certain subproblems are computed multiple times. For example, when calculating countWays(4), we recursively calculate countWays(3) and countWays(2) and countWays(1) which in turn will recursively compute countWays(2) again. This redundancy leads to overlapping subproblems.
- There is only one parameter that changes in the recursive solution and it can go from 0 to n. So we create a 1D array of size n+1 for memoization.
- We initialize this array as -1 to indicate nothing is computed initially.
- Now we modify our recursive solution to first check if the value is -1, then only make recursive calls. This way, we avoid re-computations of the same subproblems.
C++
// C++ program to count number of
// ways to reach nth stair.
#include <bits/stdc++.h>
using namespace std;
// Recursive function to count number
// of ways to reach nth stair
int countWaysRecur(int n, vector<int> &memo) {
// Base case for 0th stair
if (n == 0) return 1;
// For invalid stair, return 0.
if (n < 0) return 0;
// If n'th stair is memoized,
// return its value
if (memo[n]!=-1) return memo[n];
// Count number of ways to reach (n-1), (n-2),
// (n-3)th stair and memoize it.
return memo[n] = countWaysRecur(n-1, memo) +
countWaysRecur(n-2, memo) + countWaysRecur(n-3, memo);
}
int countWays(int n) {
vector<int> memo(n+1, -1);
return countWaysRecur(n, memo);
}
int main() {
int n = 4;
cout << countWays(n) << endl;
return 0;
}
Java
// Java program to count number of
// ways to reach nth stair.
import java.util.Arrays;
class GfG {
// Recursive function to count number
// of ways to reach nth stair
static int countWaysRecur(int n, int[] memo) {
// Base case for 0th stair
if (n == 0) return 1;
// For invalid stair, return 0.
if (n < 0) return 0;
// If n'th stair is memoized,
// return its value
if (memo[n] != -1) return memo[n];
// Count number of ways to reach (n-1), (n-2),
// (n-3)th stair and memoize it.
return memo[n] = countWaysRecur(n - 1, memo) +
countWaysRecur(n - 2, memo) +
countWaysRecur(n - 3, memo);
}
static int countWays(int n) {
int[] memo = new int[n + 1];
Arrays.fill(memo, -1);
return countWaysRecur(n, memo);
}
public static void main(String[] args) {
int n = 4;
System.out.println(countWays(n));
}
}
Python
# Python program to count number of
# ways to reach nth stair.
# Recursive function to count number
# of ways to reach nth stair
def countWaysRecur(n, memo):
# Base case for 0th stair
if n == 0:
return 1
# For invalid stair, return 0.
if n < 0:
return 0
# If n'th stair is memoized,
# return its value
if memo[n] != -1:
return memo[n]
# Count number of ways to reach (n-1), (n-2),
# (n-3)th stair and memoize it.
memo[n] = countWaysRecur(n - 1, memo) + \
countWaysRecur(n - 2, memo) + countWaysRecur(n - 3, memo)
return memo[n]
def countWays(n):
memo = [-1] * (n + 1)
return countWaysRecur(n, memo)
if __name__ == "__main__":
n = 4
print(countWays(n))
C#
// C# program to count number of
// ways to reach nth stair.
using System;
class GfG {
// Recursive function to count number
// of ways to reach nth stair
static int countWaysRecur(int n, int[] memo) {
// Base case for 0th stair
if (n == 0) return 1;
// For invalid stair, return 0.
if (n < 0) return 0;
// If n'th stair is memoized,
// return its value
if (memo[n] != -1) return memo[n];
// Count number of ways to reach (n-1), (n-2),
// (n-3)th stair and memoize it.
return memo[n] = countWaysRecur(n - 1, memo) +
countWaysRecur(n - 2, memo) +
countWaysRecur(n - 3, memo);
}
static int countWays(int n) {
int[] memo = new int[n + 1];
Array.Fill(memo, -1);
return countWaysRecur(n, memo);
}
static void Main(string[] args) {
int n = 4;
Console.WriteLine(countWays(n));
}
}
JavaScript
// JavaScript program to count number of
// ways to reach nth stair.
// Recursive function to count number
// of ways to reach nth stair
function countWaysRecur(n, memo) {
// Base case for 0th stair
if (n === 0) return 1;
// For invalid stair, return 0.
if (n < 0) return 0;
// If n'th stair is memoized,
// return its value
if (memo[n] !== -1) return memo[n];
// Count number of ways to reach (n-1), (n-2),
// (n-3)th stair and memoize it.
memo[n] = countWaysRecur(n - 1, memo) +
countWaysRecur(n - 2, memo) +
countWaysRecur(n - 3, memo);
return memo[n];
}
function countWays(n) {
let memo = new Array(n + 1).fill(-1);
return countWaysRecur(n, memo);
}
const n = 4;
console.log(countWays(n));
Using Bottom-Up DP (Tabulation) - O(n) Time and O(n) Space
The idea is to create a 1-D array, fill values for first three stairs and compute the values from 3 to n using the previous three results. For i=3 to n, do dp[i] = dp[i-1] + dp[i-2] + dp[i-3].
Below is the implementation of the above approach:
C++
// C++ program to count number of
// ways to reach nth stair.
#include <bits/stdc++.h>
using namespace std;
int countWays(int n) {
// Base case for 0th and 1st stair
if (n == 0 || n == 1)
return 1;
// base case for 2nd stair
if (n == 2)
return 2;
// Initializing a matrix of size n+1
vector<int> dp(n + 1);
// insert ans values for 0,1,2 stair
dp[0] = 1;
dp[1] = 1;
dp[2] = 2;
// building dp in bottom up manner
for (int i = 3; i <= n; i++) {
dp[i] = dp[i - 1] + dp[i - 2] + dp[i - 3];
}
return dp[n];
}
int main() {
int n = 4;
cout << countWays(n) << endl;
return 0;
}
Java
// Java program to count number of
// ways to reach nth stair.
import java.util.Arrays;
class GfG {
static int countWays(int n) {
// Base case for 0th and 1st stair
if (n == 0 || n == 1) return 1;
// base case for 2nd stair
if (n == 2) return 2;
// Initializing a matrix of size n+1
int[] dp = new int[n + 1];
// insert ans values for 0,1,2 stair
dp[0] = 1;
dp[1] = 1;
dp[2] = 2;
// building dp in bottom up manner
for (int i = 3; i <= n; i++) {
dp[i] = dp[i - 1] + dp[i - 2] + dp[i - 3];
}
return dp[n];
}
public static void main(String[] args) {
int n = 4;
System.out.println(countWays(n));
}
}
Python
# Python program to count number of
# ways to reach nth stair.
def countWays(n):
# Base case for 0th and 1st stair
if n == 0 or n == 1:
return 1
# base case for 2nd stair
if n == 2:
return 2
# Initializing a matrix of size n+1
dp = [0] * (n + 1)
# insert ans values for 0,1,2 stair
dp[0] = 1
dp[1] = 1
dp[2] = 2
# building dp in bottom up manner
for i in range(3, n + 1):
dp[i] = dp[i - 1] + dp[i - 2] + dp[i - 3]
return dp[n]
if __name__ == "__main__":
n = 4
print(countWays(n))
C#
// C# program to count number of
// ways to reach nth stair.
using System;
class GfG {
static int countWays(int n) {
// Base case for 0th and 1st stair
if (n == 0 || n == 1) return 1;
// base case for 2nd stair
if (n == 2) return 2;
// Initializing a matrix of size n+1
int[] dp = new int[n + 1];
// insert ans values for 0,1,2 stair
dp[0] = 1;
dp[1] = 1;
dp[2] = 2;
// building dp in bottom up manner
for (int i = 3; i <= n; i++) {
dp[i] = dp[i - 1] + dp[i - 2] + dp[i - 3];
}
return dp[n];
}
static void Main(string[] args) {
int n = 4;
Console.WriteLine(countWays(n));
}
}
JavaScript
// JavaScript program to count number of
// ways to reach nth stair.
function countWays(n) {
// Base case for 0th and 1st stair
if (n === 0 || n === 1) return 1;
// base case for 2nd stair
if (n === 2) return 2;
// Initializing a matrix of size n+1
let dp = new Array(n + 1).fill(0);
// insert ans values for 0,1,2 stair
dp[0] = 1;
dp[1] = 1;
dp[2] = 2;
// building dp in bottom up manner
for (let i = 3; i <= n; i++) {
dp[i] = dp[i - 1] + dp[i - 2] + dp[i - 3];
}
return dp[n];
}
const n = 4;
console.log(countWays(n));
Using Space Optimized DP - O(n) Time and O(1) Space
The idea is to store only the previous three computed values. We can observe that for a given stair, only the result of last three stairs are needed. So only store these three values and update them after each step.
Below is the implementation of the above approach:
C++
// C++ program to count number of
// ways to reach nth stair.
#include <bits/stdc++.h>
using namespace std;
int countWays(int n) {
// Base case for 0th and 1st stair
if (n == 0 || n == 1)
return 1;
// base case for 2nd stair
if (n == 2)
return 2;
// Variables to store values
// of previous 3 stairs.
int prev1, prev2, prev3;
// insert ans values for 0,1,2 stair
prev3 = 1;
prev2 = 1;
prev1 = 2;
// building dp in bottom up manner
for (int i = 3; i <= n; i++) {
int val = prev1 + prev2 + prev3;
// Replace previous stair values
// with next stairs.
prev3 = prev2;
prev2 = prev1;
prev1 = val;
}
return prev1;
}
int main() {
int n = 4;
cout << countWays(n) << endl;
return 0;
}
C
// C program to count number of
// ways to reach nth stair.
#include <stdio.h>
int countWays(int n) {
// Base case for 0th and 1st stair
if (n == 0 || n == 1)
return 1;
// base case for 2nd stair
if (n == 2)
return 2;
// Variables to store values
// of previous 3 stairs.
int prev1, prev2, prev3;
// insert ans values for 0,1,2 stair
prev3 = 1;
prev2 = 1;
prev1 = 2;
// building dp in bottom up manner
for (int i = 3; i <= n; i++) {
int val = prev1 + prev2 + prev3;
// Replace previous stair values
// with next stairs.
prev3 = prev2;
prev2 = prev1;
prev1 = val;
}
return prev1;
}
int main() {
int n = 4;
printf("%d\n", countWays(n));
return 0;
}
Java
// Java program to count number of
// ways to reach nth stair.
class GfG {
static int countWays(int n) {
// Base case for 0th and 1st stair
if (n == 0 || n == 1)
return 1;
// base case for 2nd stair
if (n == 2)
return 2;
// Variables to store values
// of previous 3 stairs.
int prev1, prev2, prev3;
// insert ans values for 0,1,2 stair
prev3 = 1;
prev2 = 1;
prev1 = 2;
// building dp in bottom up manner
for (int i = 3; i <= n; i++) {
int val = prev1 + prev2 + prev3;
// Replace previous stair values
// with next stairs.
prev3 = prev2;
prev2 = prev1;
prev1 = val;
}
return prev1;
}
public static void main(String[] args) {
int n = 4;
System.out.println(countWays(n));
}
}
Python
# Python program to count number of
# ways to reach nth stair.
def countWays(n):
# Base case for 0th and 1st stair
if n == 0 or n == 1:
return 1
# base case for 2nd stair
if n == 2:
return 2
# Variables to store values
# of previous 3 stairs.
prev3 = 1
prev2 = 1
prev1 = 2
# building dp in bottom up manner
for i in range(3, n + 1):
val = prev1 + prev2 + prev3
# Replace previous stair values
# with next stairs.
prev3 = prev2
prev2 = prev1
prev1 = val
return prev1
if __name__ == "__main__":
n = 4
print(countWays(n))
C#
// C# program to count number of
// ways to reach nth stair.
using System;
class GfG {
static int countWays(int n) {
// Base case for 0th and 1st stair
if (n == 0 || n == 1)
return 1;
// base case for 2nd stair
if (n == 2)
return 2;
// Variables to store values
// of previous 3 stairs.
int prev1, prev2, prev3;
// insert ans values for 0,1,2 stair
prev3 = 1;
prev2 = 1;
prev1 = 2;
// building dp in bottom up manner
for (int i = 3; i <= n; i++) {
int val = prev1 + prev2 + prev3;
// Replace previous stair values
// with next stairs.
prev3 = prev2;
prev2 = prev1;
prev1 = val;
}
return prev1;
}
static void Main() {
int n = 4;
Console.WriteLine(countWays(n));
}
}
JavaScript
// JavaScript program to count number of
// ways to reach nth stair.
function countWays(n) {
// Base case for 0th and 1st stair
if (n === 0 || n === 1)
return 1;
// base case for 2nd stair
if (n === 2)
return 2;
// Variables to store values
// of previous 3 stairs.
let prev3 = 1, prev2 = 1, prev1 = 2;
// building dp in bottom up manner
for (let i = 3; i <= n; i++) {
let val = prev1 + prev2 + prev3;
// Replace previous stair values
// with next stairs.
prev3 = prev2;
prev2 = prev1;
prev1 = val;
}
return prev1;
}
let n = 4;
console.log(countWays(n));
Using Matrix Exponentiation - O(log n) Time and O(1) Space
The recurrence relation for a given step is given as countWays(n) = countWays(n-1) + countWays(n-2) + countWays(n-3) starting with countWays(0)=1, countWays(1)=1, countWays(2)=2.
Refer to Matrix Exponentiation to understand how matrix exponentiation works.
Below is the implementation of the above approach:
C++
// C++ program to count number of
// ways to reach nth stair.
#include <bits/stdc++.h>
using namespace std;
// Function to multiply two 3x3 matrices
void multiply(vector<vector<int> >& a,
vector<vector<int> >& b) {
// Matrix to store the result
vector<vector<int> > c(3, vector<int>(3));
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 3; j++) {
for (int k = 0; k < 3; k++) {
c[i][j]
= (c[i][j] + ((a[i][k]) * (b[k][j])));
}
}
}
// Copy the result back to the first matrix
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 3; j++) {
a[i][j] = c[i][j];
}
}
}
// Function to calculate (Matrix M) ^ expo
vector<vector<int> >
power(vector<vector<int> > m, int expo) {
// Initialize result with identity matrix
vector<vector<int> > ans
= { { 1, 0, 0 }, { 0, 1, 0 }, { 0, 0, 1 } };
// Fast Exponentiation
while (expo) {
if (expo & 1)
multiply(ans, m);
multiply(m, m);
expo >>= 1;
}
return ans;
}
// function to count number of
// ways to reach nth stair.
int countWays(int n) {
// base condition
if (n == 0 || n == 1)
return 1;
// Matrix M to generate the next step value.
vector<vector<int> > m
= { { 1, 1, 1 }, { 1, 0, 0 }, { 0, 1, 0 } };
// first 3 values of steps are:
// findWays(0) = 1
// findWays(1) = 1
// findWays(2) = 2
// f = {{findWays(2), 0, 0}, {findWays(1), 0, 0},
// {findWays(0), 0,0}}
vector<vector<int> > f
= { { 2, 0, 0 }, { 1, 0, 0 }, { 1, 0, 0 } };
vector<vector<int> > res = power(m, n - 2);
multiply(res, f);
return res[0][0];
}
int main() {
int n = 4;
cout << countWays(n) << endl;
return 0;
}
Java
// Java program to count number of
// ways to reach nth stair.
import java.util.Arrays;
class GfG {
// Function to multiply two 3x3 matrices
static void multiply(int[][] a, int[][] b) {
// Matrix to store the result
int[][] c = new int[3][3];
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 3; j++) {
for (int k = 0; k < 3; k++) {
c[i][j] = c[i][j] + (a[i][k] * b[k][j]);
}
}
}
// Copy the result back to the first matrix
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 3; j++) {
a[i][j] = c[i][j];
}
}
}
// Function to calculate (Matrix M) ^ expo
static int[][] power(int[][] m, int expo) {
// Initialize result with identity matrix
int[][] ans = { {1, 0, 0}, {0, 1, 0}, {0, 0, 1} };
// Fast Exponentiation
while (expo != 0) {
if ((expo & 1) != 0) multiply(ans, m);
multiply(m, m);
expo >>= 1;
}
return ans;
}
// function to count number of
// ways to reach nth stair.
static int countWays(int n) {
// base condition
if (n == 0 || n == 1) return 1;
// Matrix M to generate the next step value.
int[][] m = { {1, 1, 1}, {1, 0, 0}, {0, 1, 0} };
// first 3 values of steps are:
// findWays(0) = 1
// findWays(1) = 1
// findWays(2) = 2
// f = {{findWays(2), 0, 0}, {findWays(1), 0, 0},
// {findWays(0), 0,0}}
int[][] f = { {2, 0, 0}, {1, 0, 0}, {1, 0, 0} };
int[][] res = power(m, n - 2);
multiply(res, f);
return res[0][0];
}
public static void main(String[] args) {
int n = 4;
System.out.println(countWays(n));
}
}
Python
# Python program to count number of
# ways to reach nth stair.
# Function to multiply two 3x3 matrices
def multiply(a, b):
# Matrix to store the result
c = [[0] * 3 for _ in range(3)]
for i in range(3):
for j in range(3):
for k in range(3):
c[i][j] += a[i][k] * b[k][j]
# Copy the result back to the first matrix
for i in range(3):
for j in range(3):
a[i][j] = c[i][j]
# Function to calculate (Matrix M) ^ expo
def power(m, expo):
# Initialize result with identity matrix
ans = [[1, 0, 0], [0, 1, 0], [0, 0, 1]]
# Fast Exponentiation
while expo:
if expo & 1:
multiply(ans, m)
multiply(m, m)
expo >>= 1
return ans
# function to count number of
# ways to reach nth stair.
def countWays(n):
# base condition
if n == 0 or n == 1:
return 1
# Matrix M to generate the next step value.
m = [[1, 1, 1], [1, 0, 0], [0, 1, 0]]
# first 3 values of steps are:
# findWays(0) = 1
# findWays(1) = 1
# findWays(2) = 2
# f = {{findWays(2), 0, 0}, {findWays(1), 0, 0},
# {findWays(0), 0,0}}
f = [[2, 0, 0], [1, 0, 0], [1, 0, 0]]
res = power(m, n - 2)
multiply(res, f)
return res[0][0]
if __name__ == "__main__":
n = 4
print(countWays(n))
C#
// C# program to count number of
// ways to reach nth stair.
using System;
class GfG {
// Function to multiply two 3x3 matrices
static void multiply(int[,] a, int[,] b) {
// Matrix to store the result
int[,] c = new int[3, 3];
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 3; j++) {
for (int k = 0; k < 3; k++) {
c[i, j] += a[i, k] * b[k, j];
}
}
}
// Copy the result back to the first matrix
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 3; j++) {
a[i, j] = c[i, j];
}
}
}
// Function to calculate (Matrix M) ^ expo
static int[,] power(int[,] m, int expo) {
// Initialize result with identity matrix
int[,] ans = { { 1, 0, 0 }, { 0, 1, 0 }, { 0, 0, 1 } };
// Fast Exponentiation
while (expo != 0) {
if ((expo & 1) != 0)
multiply(ans, m);
multiply(m, m);
expo >>= 1;
}
return ans;
}
// function to count number of
// ways to reach nth stair.
static int countWays(int n) {
// base condition
if (n == 0 || n == 1)
return 1;
// Matrix M to generate the next step value.
int[,] m = { { 1, 1, 1 }, { 1, 0, 0 }, { 0, 1, 0 } };
// first 3 values of steps are:
// findWays(0) = 1
// findWays(1) = 1
// findWays(2) = 2
// f = {{findWays(2), 0, 0}, {findWays(1), 0, 0},
// {findWays(0), 0,0}}
int[,] f = { { 2, 0, 0 }, { 1, 0, 0 }, { 1, 0, 0 } };
int[,] res = power(m, n - 2);
multiply(res, f);
return res[0, 0];
}
static void Main(string[] args) {
int n = 4;
Console.WriteLine(countWays(n));
}
}
JavaScript
// JavaScript program to count number of
// ways to reach nth stair
// Function to multiply two 3x3 matrices
function multiply(a, b) {
// Matrix to store the result
let c = Array.from({ length: 3 }, () => Array(3).fill(0));
for (let i = 0; i < 3; i++) {
for (let j = 0; j < 3; j++) {
for (let k = 0; k < 3; k++) {
c[i][j] += a[i][k] * b[k][j];
}
}
}
// Copy the result back to the first matrix
for (let i = 0; i < 3; i++) {
for (let j = 0; j < 3; j++) {
a[i][j] = c[i][j];
}
}
}
// Function to calculate (Matrix M) ^ expo
function power(m, expo) {
// Initialize result with identity matrix
let ans = [[1, 0, 0], [0, 1, 0], [0, 0, 1]];
// Fast Exponentiation
while (expo) {
if (expo & 1) {
multiply(ans, m);
}
multiply(m, m);
expo >>= 1;
}
return ans;
}
// function to count number of
// ways to reach nth stair.
function countWays(n) {
// base condition
if (n === 0 || n === 1) return 1;
// Matrix M to generate the next step value.
let m = [[1, 1, 1], [1, 0, 0], [0, 1, 0]];
// first 3 values of steps are:
// findWays(0) = 1
// findWays(1) = 1
// findWays(2) = 2
// f = {{findWays(2), 0, 0}, {findWays(1), 0, 0},
// {findWays(0), 0,0}}
let f = [[2, 0, 0], [1, 0, 0], [1, 0, 0]];
let res = power(m, n - 2);
multiply(res, f);
return res[0][0];
}
let n = 4;
console.log(countWays(n));
Explore
DSA Fundamentals
Data Structures
Algorithms
Advanced
Interview Preparation
Practice Problem