diff --git a/kamyshov_danila_lab_6/README.md b/kamyshov_danila_lab_6/README.md new file mode 100644 index 0000000..24726c0 --- /dev/null +++ b/kamyshov_danila_lab_6/README.md @@ -0,0 +1,37 @@ +# Лабораторная работа №6 - Определение детерминанта матрицы с помощью параллельных вычислений + +Задание: + +Кратко: реализовать нахождение детерминанта квадратной матрицы. Что такое детерминант матрицы (или определитель) можно посмотреть по ссылке. + +Подробно: в лабораторной работе требуется сделать два алгоритма: обычный и параллельный (задание со * - реализовать это в рамках одного алгоритма). В параллельном алгоритме предусмотреть ручное задание количества потоков (число потоков = 1 как раз и реализует задание со *), каждый из которых будет выполнять нахождение отдельной группы множителей. + +Сделать несколько бенчмарков последовательного и параллельного алгоритма поиска детерминанта матрицы размером 100x100, 300x300, 500x500 элементов. Отразить свои наблюдения в readme-отчете. + +

+

Код
+ +

+

+

Код
+ +

+

+

Код
+ +

+

+

Код
+ +

+

+

Работа программы
+ +

+ +Вывод: Параллельный алгоритм в условии данной задачи не имеет смысла использовать + + +# Видео + +Видео с разбором лабораторной - https://drive.google.com/file/d/1Y-dOFRhrAD9epoUAQGOWEEsSCeHMMpIy/view?usp=sharing diff --git a/kamyshov_danila_lab_6/screens/img1.png b/kamyshov_danila_lab_6/screens/img1.png new file mode 100644 index 0000000..0687d40 Binary files /dev/null and b/kamyshov_danila_lab_6/screens/img1.png differ diff --git a/kamyshov_danila_lab_6/screens/img2.png b/kamyshov_danila_lab_6/screens/img2.png new file mode 100644 index 0000000..fc67411 Binary files /dev/null and b/kamyshov_danila_lab_6/screens/img2.png differ diff --git a/kamyshov_danila_lab_6/screens/img3.png b/kamyshov_danila_lab_6/screens/img3.png new file mode 100644 index 0000000..afa817f Binary files /dev/null and b/kamyshov_danila_lab_6/screens/img3.png differ diff --git a/kamyshov_danila_lab_6/screens/img4.png b/kamyshov_danila_lab_6/screens/img4.png new file mode 100644 index 0000000..a832637 Binary files /dev/null and b/kamyshov_danila_lab_6/screens/img4.png differ diff --git a/kamyshov_danila_lab_6/screens/img5.png b/kamyshov_danila_lab_6/screens/img5.png new file mode 100644 index 0000000..8a1cfb9 Binary files /dev/null and b/kamyshov_danila_lab_6/screens/img5.png differ diff --git a/kamyshov_danila_lab_6/src/main/java/org/example/MatrixDeterminant.java b/kamyshov_danila_lab_6/src/main/java/org/example/MatrixDeterminant.java new file mode 100644 index 0000000..d1573af --- /dev/null +++ b/kamyshov_danila_lab_6/src/main/java/org/example/MatrixDeterminant.java @@ -0,0 +1,104 @@ +package org.example; + +import org.apache.commons.math3.linear.LUDecomposition; +import org.apache.commons.math3.linear.MatrixUtils; +import org.apache.commons.math3.linear.RealMatrix; + +import java.util.Scanner; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; + +public class MatrixDeterminant { + + static double[][] generateRandomSquareMatrix(int size) { + double[][] matrix = new double[size][size]; + for (int i = 0; i < size; i++) { + for (int j = 0; j < size; j++) { + matrix[i][j] = Math.random() * 10; + } + } + return matrix; + } + + static double sequentialMatrixDeterminant(double[][] matrix) { + RealMatrix realMatrix = MatrixUtils.createRealMatrix(matrix); + LUDecomposition luDecomposition = new LUDecomposition(realMatrix); + return luDecomposition.getDeterminant(); + } + + static double[] parallelMatrixDeterminant(double[][] matrix, int numThreads) { + int rows = matrix.length; + int cols = matrix[0].length; + int chunkSize = rows / numThreads; + + double[] determinants = new double[numThreads]; + + class CalculateDeterminantTask implements Runnable { + private final int startRow; + private final int endRow; + private final double[][] submatrix; + + CalculateDeterminantTask(int startRow, int endRow, double[][] submatrix) { + this.startRow = startRow; + this.endRow = endRow; + this.submatrix = submatrix; + } + + @Override + public void run() { + RealMatrix realSubmatrix = MatrixUtils.createRealMatrix(submatrix); + LUDecomposition luDecomposition = new LUDecomposition(realSubmatrix); + determinants[startRow / chunkSize] = luDecomposition.getDeterminant(); + } + } + + ExecutorService executorService = Executors.newFixedThreadPool(numThreads); + + for (int i = 0; i < numThreads; i++) { + int startRow = i * chunkSize; + int endRow = (i + 1) * chunkSize; + double[][] submatrix = new double[chunkSize][cols]; + System.arraycopy(matrix, startRow, submatrix, 0, chunkSize); + executorService.submit(new CalculateDeterminantTask(startRow, endRow, submatrix)); + } + + executorService.shutdown(); + + while (!executorService.isTerminated()) { + // Ждем, пока все потоки завершат работу + } + + return determinants; + } + + static void benchmark(int matrixSize, int numThreads) { + double[][] matrix = generateRandomSquareMatrix(matrixSize); + + long startTime = System.currentTimeMillis(); + double sequentialResult = sequentialMatrixDeterminant(matrix); + long sequentialTime = System.currentTimeMillis() - startTime; + + startTime = System.currentTimeMillis(); + double[] parallelResult = parallelMatrixDeterminant(matrix, numThreads); + long parallelTime = System.currentTimeMillis() - startTime; + + System.out.println("Matrix size: " + matrixSize + "x" + matrixSize); + System.out.println("Sequential algorithm time: " + sequentialTime + " milliseconds"); + System.out.println("Parallel algorithm time (" + numThreads + " threads): " + parallelTime + " milliseconds"); + System.out.println("=============================="); + } + + public static void main(String[] args) { + int[] matrixSizes = {100, 300, 500}; + Scanner scanner = new Scanner(System.in); + + System.out.print("Введите количество потоков: "); + int numThreads = scanner.nextInt(); + + for (int size : matrixSizes) { + benchmark(size, numThreads); + } + + scanner.close(); + } +}