forked from Alexey/DAS_2024_1
81 lines
2.7 KiB
Java
81 lines
2.7 KiB
Java
import java.util.ArrayList;
|
|
import java.util.List;
|
|
import java.util.concurrent.ExecutionException;
|
|
import java.util.concurrent.ExecutorService;
|
|
import java.util.concurrent.Executors;
|
|
import java.util.concurrent.Future;
|
|
|
|
public class DeterminantCalculator {
|
|
public static int calculateDeterminant(int[][] matrix, int numThreads) throws InterruptedException, ExecutionException {
|
|
int size = matrix.length;
|
|
|
|
// Если размер матрицы 1x1, возвращаем единственный элемент.
|
|
if (size == 1) {
|
|
return matrix[0][0];
|
|
}
|
|
|
|
// Если количество потоков равно 1, выполняем последовательный алгоритм.
|
|
if (numThreads == 1) {
|
|
return sequentialDeterminant(matrix);
|
|
}
|
|
|
|
// Иначе выполняем параллельный алгоритм.
|
|
return parallelDeterminant(matrix, numThreads);
|
|
}
|
|
|
|
private static int sequentialDeterminant(int[][] matrix) {
|
|
int size = matrix.length;
|
|
if (size == 1) {
|
|
return matrix[0][0];
|
|
}
|
|
if (size == 2) {
|
|
return matrix[0][0] * matrix[1][1] - matrix[0][1] * matrix[1][0];
|
|
}
|
|
|
|
int determinant = 0;
|
|
for (int col = 0; col < size; col++) {
|
|
determinant += (int) (Math.pow(-1, col) * matrix[0][col] * sequentialDeterminant(getMinor(matrix, 0, col)));
|
|
}
|
|
return determinant;
|
|
}
|
|
|
|
private static int parallelDeterminant(int[][] matrix, int numThreads) throws InterruptedException, ExecutionException {
|
|
int size = matrix.length;
|
|
ExecutorService executor = Executors.newFixedThreadPool(numThreads);
|
|
List<Future<Double>> futures = new ArrayList<>();
|
|
|
|
for (int col = 0; col < size; col++) {
|
|
int finalCol = col;
|
|
futures.add(executor.submit(() -> {
|
|
double minorDet = sequentialDeterminant(getMinor(matrix, 0, finalCol));
|
|
return Math.pow(-1, finalCol) * matrix[0][finalCol] * minorDet;
|
|
}));
|
|
}
|
|
|
|
int determinant = 0;
|
|
for (Future<Double> future : futures) {
|
|
determinant += future.get();
|
|
}
|
|
|
|
executor.shutdown();
|
|
return determinant;
|
|
}
|
|
|
|
private static int[][] getMinor(int[][] matrix, int row, int col) {
|
|
int size = matrix.length;
|
|
int[][] minor = new int[size - 1][size - 1];
|
|
|
|
for (int i = 0, mi = 0; i < size; i++) {
|
|
if (i == row) continue;
|
|
for (int j = 0, mj = 0; j < size; j++) {
|
|
if (j == col) continue;
|
|
minor[mi][mj] = matrix[i][j];
|
|
mj++;
|
|
}
|
|
mi++;
|
|
}
|
|
return minor;
|
|
}
|
|
}
|
|
|