1
1
package com .thealgorithms .matrix .matrixexponentiation ;
2
2
3
+ import java .math .BigDecimal ;
3
4
import java .util .Scanner ;
4
5
6
+ import com .thealgorithms .matrix .utils .MatrixUtil ;
7
+
5
8
/**
6
9
* @author Anirudh Buvanesh (https://github.com/anirudhb11) For more information
7
10
* see https://www.geeksforgeeks.org/matrix-exponentiation/
@@ -12,39 +15,13 @@ private Fibonacci() {
12
15
}
13
16
14
17
// Exponentiation matrix for Fibonacci sequence
15
- private static final int [][] FIB_MATRIX = {{1 , 1 }, {1 , 0 }};
16
- private static final int [][] IDENTITY_MATRIX = {{1 , 0 }, {0 , 1 }};
17
- // First 2 fibonacci numbers
18
- private static final int [][] BASE_FIB_NUMBERS = {{1 }, {0 }};
19
-
20
- /**
21
- * Performs multiplication of 2 matrices
22
- *
23
- * @param matrix1
24
- * @param matrix2
25
- * @return The product of matrix1 and matrix2
26
- */
27
- private static int [][] matrixMultiplication (int [][] matrix1 , int [][] matrix2 ) {
28
- // Check if matrices passed can be multiplied
29
- int rowsInMatrix1 = matrix1 .length ;
30
- int columnsInMatrix1 = matrix1 [0 ].length ;
18
+ private static final BigDecimal ONE = BigDecimal .valueOf (1 );
19
+ private static final BigDecimal ZERO = BigDecimal .valueOf (0 );
31
20
32
- int rowsInMatrix2 = matrix2 .length ;
33
- int columnsInMatrix2 = matrix2 [0 ].length ;
34
-
35
- assert columnsInMatrix1 == rowsInMatrix2 ;
36
- int [][] product = new int [rowsInMatrix1 ][columnsInMatrix2 ];
37
- for (int rowIndex = 0 ; rowIndex < rowsInMatrix1 ; rowIndex ++) {
38
- for (int colIndex = 0 ; colIndex < columnsInMatrix2 ; colIndex ++) {
39
- int matrixEntry = 0 ;
40
- for (int intermediateIndex = 0 ; intermediateIndex < columnsInMatrix1 ; intermediateIndex ++) {
41
- matrixEntry += matrix1 [rowIndex ][intermediateIndex ] * matrix2 [intermediateIndex ][colIndex ];
42
- }
43
- product [rowIndex ][colIndex ] = matrixEntry ;
44
- }
45
- }
46
- return product ;
47
- }
21
+ private static final BigDecimal [][] FIB_MATRIX = {{ONE , ONE }, {ONE , ZERO }};
22
+ private static final BigDecimal [][] IDENTITY_MATRIX = {{ONE , ZERO }, {ZERO , ONE }};
23
+ // First 2 fibonacci numbers
24
+ private static final BigDecimal [][] BASE_FIB_NUMBERS = {{ONE }, {ZERO }};
48
25
49
26
/**
50
27
* Calculates the fibonacci number using matrix exponentiaition technique
@@ -53,16 +30,16 @@ private static int[][] matrixMultiplication(int[][] matrix1, int[][] matrix2) {
53
30
* Outputs the nth * fibonacci number
54
31
* @return a 2 X 1 array as { {F_n+1}, {F_n} }
55
32
*/
56
- public static int [][] fib (int n ) {
33
+ public static BigDecimal [][] fib (int n ) {
57
34
if (n == 0 ) {
58
35
return IDENTITY_MATRIX ;
59
36
} else {
60
- int [][] cachedResult = fib (n / 2 );
61
- int [][] matrixExpResult = matrixMultiplication (cachedResult , cachedResult );
37
+ BigDecimal [][] cachedResult = fib (n / 2 );
38
+ BigDecimal [][] matrixExpResult = MatrixUtil . multiply (cachedResult , cachedResult ). get ( );
62
39
if (n % 2 == 0 ) {
63
40
return matrixExpResult ;
64
41
} else {
65
- return matrixMultiplication (FIB_MATRIX , matrixExpResult );
42
+ return MatrixUtil . multiply (FIB_MATRIX , matrixExpResult ). get ( );
66
43
}
67
44
}
68
45
}
@@ -71,7 +48,7 @@ public static void main(String[] args) {
71
48
// Returns [0, 1, 1, 2, 3, 5 ..] for n = [0, 1, 2, 3, 4, 5.. ]
72
49
Scanner sc = new Scanner (System .in );
73
50
int n = sc .nextInt ();
74
- int [][] result = matrixMultiplication (fib (n ), BASE_FIB_NUMBERS );
51
+ BigDecimal [][] result = MatrixUtil . multiply (fib (n ), BASE_FIB_NUMBERS ). get ( );
75
52
System .out .println ("Fib(" + n + ") = " + result [1 ][0 ]);
76
53
sc .close ();
77
54
}
0 commit comments