aleikin_artem_lab_6 #227
16
.gitignore
vendored
Normal file
16
.gitignore
vendored
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
################################################################################
|
||||||
|
# Данный GITIGNORE-файл был автоматически создан Microsoft(R) Visual Studio.
|
||||||
|
################################################################################
|
||||||
|
|
||||||
|
/.vs
|
||||||
|
/aleikin_artem_lab_3
|
||||||
|
/aleikin_artem_lab_4
|
||||||
|
/aleikin_artem_lab_5/MultiplyMatrix
|
||||||
|
/aleikin_artem_lab_6/DerminantMatrix/.vs/DerminantMatrix
|
||||||
|
/aleikin_artem_lab_6/DerminantMatrix/bin/Debug/net8.0
|
||||||
|
/aleikin_artem_lab_6/DerminantMatrix/obj
|
||||||
|
/dozorova_alena_lab_2
|
||||||
|
/dozorova_alena_lab_3
|
||||||
|
/dozorova_alena_lab_4
|
||||||
|
/dozorova_alena_lab_5/ConsoleApp1/obj
|
||||||
|
/dozorova_alena_lab_6/ConsoleApp1/obj
|
10
aleikin_artem_lab_6/DerminantMatrix/DerminantMatrix.csproj
Normal file
10
aleikin_artem_lab_6/DerminantMatrix/DerminantMatrix.csproj
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<OutputType>Exe</OutputType>
|
||||||
|
<TargetFramework>net8.0</TargetFramework>
|
||||||
|
<ImplicitUsings>enable</ImplicitUsings>
|
||||||
|
<Nullable>enable</Nullable>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
</Project>
|
25
aleikin_artem_lab_6/DerminantMatrix/DerminantMatrix.sln
Normal file
25
aleikin_artem_lab_6/DerminantMatrix/DerminantMatrix.sln
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
|
||||||
|
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||||
|
# Visual Studio Version 17
|
||||||
|
VisualStudioVersion = 17.11.35312.102
|
||||||
|
MinimumVisualStudioVersion = 10.0.40219.1
|
||||||
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "DerminantMatrix", "DerminantMatrix.csproj", "{40E2A332-5A1C-46A7-AFA9-833E4922AD08}"
|
||||||
|
EndProject
|
||||||
|
Global
|
||||||
|
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||||
|
Debug|Any CPU = Debug|Any CPU
|
||||||
|
Release|Any CPU = Release|Any CPU
|
||||||
|
EndGlobalSection
|
||||||
|
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||||
|
{40E2A332-5A1C-46A7-AFA9-833E4922AD08}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{40E2A332-5A1C-46A7-AFA9-833E4922AD08}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{40E2A332-5A1C-46A7-AFA9-833E4922AD08}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{40E2A332-5A1C-46A7-AFA9-833E4922AD08}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
EndGlobalSection
|
||||||
|
GlobalSection(SolutionProperties) = preSolution
|
||||||
|
HideSolutionNode = FALSE
|
||||||
|
EndGlobalSection
|
||||||
|
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||||
|
SolutionGuid = {DF40653A-B248-4AC9-8203-1F8E8EA9423F}
|
||||||
|
EndGlobalSection
|
||||||
|
EndGlobal
|
118
aleikin_artem_lab_6/DerminantMatrix/Program.cs
Normal file
118
aleikin_artem_lab_6/DerminantMatrix/Program.cs
Normal file
@ -0,0 +1,118 @@
|
|||||||
|
using System;
|
||||||
|
using System.Diagnostics;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
|
class Program
|
||||||
|
{
|
||||||
|
static void Main(string[] args)
|
||||||
|
{
|
||||||
|
int[] sizes = { 10, 11, 12 };
|
||||||
|
|
||||||
|
int maxThreads = 20;
|
||||||
|
|
||||||
|
foreach (var size in sizes)
|
||||||
|
{
|
||||||
|
Console.WriteLine($"\nРазмер матрицы: {size}x{size}");
|
||||||
|
|
||||||
|
// Генерация матрицы
|
||||||
|
var matrix = GenerateMatrix(size);
|
||||||
|
|
||||||
|
// Последовательное нахождение детерминанта
|
||||||
|
var stopwatch = Stopwatch.StartNew();
|
||||||
|
var detSequential = DeterminantSequential(matrix);
|
||||||
|
stopwatch.Stop();
|
||||||
|
long timeSequential = stopwatch.ElapsedMilliseconds;
|
||||||
|
Console.WriteLine($"Последовательное вычисление: {timeSequential} мс, детерминант = {detSequential}");
|
||||||
|
|
||||||
|
// Параллельное нахождение детерминанта
|
||||||
|
Console.WriteLine("Параллельное вычисление (время выполнения для каждого количества потоков):");
|
||||||
|
for (int threads = 1; threads <= maxThreads; threads++)
|
||||||
|
{
|
||||||
|
stopwatch.Restart();
|
||||||
|
var detParallel = DeterminantParallel(matrix, threads);
|
||||||
|
stopwatch.Stop();
|
||||||
|
long timeParallel = stopwatch.ElapsedMilliseconds;
|
||||||
|
Console.WriteLine($"Потоков: {threads} — {timeParallel} мс");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Генерация квадратной матрицы размером size x size
|
||||||
|
static double[,] GenerateMatrix(int size)
|
||||||
|
{
|
||||||
|
var random = new Random();
|
||||||
|
var matrix = new double[size, size];
|
||||||
|
for (int i = 0; i < size; i++)
|
||||||
|
for (int j = 0; j < size; j++)
|
||||||
|
matrix[i, j] = random.Next(-10, 10);
|
||||||
|
return matrix;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Последовательное вычисление детерминанта
|
||||||
|
static double DeterminantSequential(double[,] matrix)
|
||||||
|
{
|
||||||
|
int size = matrix.GetLength(0);
|
||||||
|
if (size == 1)
|
||||||
|
return matrix[0, 0];
|
||||||
|
|
||||||
|
if (size == 2)
|
||||||
|
return matrix[0, 0] * matrix[1, 1] - matrix[0, 1] * matrix[1, 0];
|
||||||
|
|
||||||
|
double determinant = 0;
|
||||||
|
for (int col = 0; col < size; col++)
|
||||||
|
{
|
||||||
|
determinant += Math.Pow(-1, col) * matrix[0, col] * DeterminantSequential(Minor(matrix, 0, col));
|
||||||
|
}
|
||||||
|
return determinant;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Параллельное вычисление детерминанта
|
||||||
|
static double DeterminantParallel(double[,] matrix, int threadCount)
|
||||||
|
{
|
||||||
|
int size = matrix.GetLength(0);
|
||||||
|
if (size == 1)
|
||||||
|
return matrix[0, 0];
|
||||||
|
|
||||||
|
if (size == 2)
|
||||||
|
return matrix[0, 0] * matrix[1, 1] - matrix[0, 1] * matrix[1, 0];
|
||||||
|
|
||||||
|
double determinant = 0;
|
||||||
|
object lockObject = new object();
|
||||||
|
|
||||||
|
Parallel.For(0, size, new ParallelOptions { MaxDegreeOfParallelism = threadCount }, col =>
|
||||||
|
{
|
||||||
|
double minorDeterminant = DeterminantSequential(Minor(matrix, 0, col));
|
||||||
|
double term = Math.Pow(-1, col) * matrix[0, col] * minorDeterminant;
|
||||||
|
|
||||||
|
lock (lockObject)
|
||||||
|
{
|
||||||
|
determinant += term;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
return determinant;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Создание минора для матрицы
|
||||||
|
static double[,] Minor(double[,] matrix, int row, int col)
|
||||||
|
{
|
||||||
|
int size = matrix.GetLength(0);
|
||||||
|
var minor = new double[size - 1, size - 1];
|
||||||
|
|
||||||
|
for (int i = 0, minorRow = 0; i < size; i++)
|
||||||
|
{
|
||||||
|
if (i == row) continue;
|
||||||
|
|
||||||
|
for (int j = 0, minorCol = 0; j < size; j++)
|
||||||
|
{
|
||||||
|
if (j == col) continue;
|
||||||
|
|
||||||
|
minor[minorRow, minorCol] = matrix[i, j];
|
||||||
|
minorCol++;
|
||||||
|
}
|
||||||
|
minorRow++;
|
||||||
|
}
|
||||||
|
|
||||||
|
return minor;
|
||||||
|
}
|
||||||
|
}
|
BIN
aleikin_artem_lab_6/Images/Отчет1.png
Normal file
BIN
aleikin_artem_lab_6/Images/Отчет1.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 104 KiB |
95
aleikin_artem_lab_6/readme.md
Normal file
95
aleikin_artem_lab_6/readme.md
Normal file
@ -0,0 +1,95 @@
|
|||||||
|
# Лабораторная работа 6 - Параллельный поиск значения детерминанта матрицы
|
||||||
|
## ПИбд-42 || Алейкин Артем
|
||||||
|
|
||||||
|
### Описание
|
||||||
|
В данной лабораторной работе мы занимались написанием многопоточного вычислителя детерминанта больших матриц.
|
||||||
|
|
||||||
|
### Объяснения
|
||||||
|
Последовательный алгоритм:
|
||||||
|
Нахождение детерминанта реализовано рекурсивно через формулу разложения по строке матрицы.
|
||||||
|
Метод DeterminantSequential вычисляет детерминант через разложение по первой строке и вызов минора.
|
||||||
|
|
||||||
|
```
|
||||||
|
static double DeterminantSequential(double[,] matrix)
|
||||||
|
{
|
||||||
|
int size = matrix.GetLength(0);
|
||||||
|
if (size == 1)
|
||||||
|
return matrix[0, 0];
|
||||||
|
|
||||||
|
if (size == 2)
|
||||||
|
return matrix[0, 0] * matrix[1, 1] - matrix[0, 1] * matrix[1, 0];
|
||||||
|
|
||||||
|
double determinant = 0;
|
||||||
|
for (int col = 0; col < size; col++)
|
||||||
|
{
|
||||||
|
determinant += Math.Pow(-1, col) * matrix[0, col] * DeterminantSequential(Minor(matrix, 0, col));
|
||||||
|
}
|
||||||
|
return determinant;
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Параллельный алгоритм:
|
||||||
|
Каждую итерацию разложения по строке матрицы можно выполнять в отдельном потоке.
|
||||||
|
DeterminantParallel использует Parallel.For для запуска потоков.
|
||||||
|
|
||||||
|
```
|
||||||
|
static double DeterminantParallel(double[,] matrix, int threadCount)
|
||||||
|
{
|
||||||
|
int size = matrix.GetLength(0);
|
||||||
|
if (size == 1)
|
||||||
|
return matrix[0, 0];
|
||||||
|
|
||||||
|
if (size == 2)
|
||||||
|
return matrix[0, 0] * matrix[1, 1] - matrix[0, 1] * matrix[1, 0];
|
||||||
|
|
||||||
|
double determinant = 0;
|
||||||
|
object lockObject = new object();
|
||||||
|
|
||||||
|
Parallel.For(0, size, new ParallelOptions { MaxDegreeOfParallelism = threadCount }, col =>
|
||||||
|
{
|
||||||
|
double minorDeterminant = DeterminantSequential(Minor(matrix, 0, col));
|
||||||
|
double term = Math.Pow(-1, col) * matrix[0, col] * minorDeterminant;
|
||||||
|
|
||||||
|
lock (lockObject)
|
||||||
|
{
|
||||||
|
determinant += term;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
return determinant;
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Миноры:
|
||||||
|
Метод Minor создает подматрицу, исключая заданные строку и столбец.
|
||||||
|
|
||||||
|
```
|
||||||
|
static double[,] Minor(double[,] matrix, int row, int col)
|
||||||
|
{
|
||||||
|
int size = matrix.GetLength(0);
|
||||||
|
var minor = new double[size - 1, size - 1];
|
||||||
|
|
||||||
|
for (int i = 0, minorRow = 0; i < size; i++)
|
||||||
|
{
|
||||||
|
if (i == row) continue;
|
||||||
|
|
||||||
|
for (int j = 0, minorCol = 0; j < size; j++)
|
||||||
|
{
|
||||||
|
if (j == col) continue;
|
||||||
|
|
||||||
|
minor[minorRow, minorCol] = matrix[i, j];
|
||||||
|
minorCol++;
|
||||||
|
}
|
||||||
|
minorRow++;
|
||||||
|
}
|
||||||
|
|
||||||
|
return minor;
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
В результате мы получаем следующие значения:
|
||||||
|
![Вычисление детерминанта матриц](./Images/Отчет1.png)
|
||||||
|
|
||||||
|
Результаты аналогичны с предыдущей лабораторной работой, многопоточный подход позволяет кратно выигрывать время, но и ресурсы на организацию работы всех потоков тоже существенны.
|
||||||
|
|
||||||
|
Видео демонстрации работы: https://vk.com/video248424990_456239613?list=ln-tyTv9vKdAOzQyPm5Y3
|
Loading…
Reference in New Issue
Block a user