180 lines
5.9 KiB
Java

import java.io.*;
import java.util.*;
import java.util.concurrent.*;
public class Main {
public static int[][] generateMatrix(int rows, int cols) {
int[][] matrix = new int[rows][cols];
Random random = new Random();
for (int i = 0; i < rows; i++) {
for (int j = 0; j < cols; j++) {
matrix[i][j] = random.nextInt(100);
}
}
return matrix;
}
public static void writeMatrixToFile(int[][] matrix, String filename) throws IOException {
try (BufferedWriter writer = new BufferedWriter(new FileWriter(filename))) {
for (int[] row : matrix) {
for (int value : row) {
writer.write(value + " ");
}
writer.newLine();
}
}
}
public static int[][] readMatrixFromFile(String filename, int rows, int cols) throws IOException {
int[][] matrix = new int[rows][cols];
try (BufferedReader reader = new BufferedReader(new FileReader(filename))) {
for (int i = 0; i < rows; i++) {
String[] values = reader.readLine().trim().split(" ");
for (int j = 0; j < cols; j++) {
matrix[i][j] = Integer.parseInt(values[j]);
}
}
}
return matrix;
}
public static void singleThreadedSort(int[][] matrix) {
int cols = matrix[0].length;
int rows = matrix.length;
int[] columnSums = new int[cols];
for (int j = 0; j < cols; j++) {
for (int i = 0; i < rows; i++) {
columnSums[j] += matrix[i][j];
}
}
sortColumns(matrix, columnSums);
}
public static void multiThreadedSortWithThreadPool(int[][] matrix, int numThreads) throws InterruptedException {
int cols = matrix[0].length;
int rows = matrix.length;
ExecutorService executor = Executors.newFixedThreadPool(numThreads);
int[] columnSums = new int[cols];
for (int j = 0; j < cols; j++) {
final int col = j;
executor.submit(() -> {
for (int i = 0; i < rows; i++) {
columnSums[col] += matrix[i][col];
}
});
}
executor.shutdown();
executor.awaitTermination(1, TimeUnit.MINUTES);
sortColumns(matrix, columnSums);
}
public static void multiThreadedSortWithForkJoin(int[][] matrix) {
int cols = matrix[0].length;
int rows = matrix.length;
int[] columnSums = new int[cols];
ForkJoinPool pool = new ForkJoinPool();
pool.invoke(new ColumnSumTask(matrix, columnSums, 0, cols - 1));
sortColumns(matrix, columnSums);
}
static class ColumnSumTask extends RecursiveAction {
private final int[][] matrix;
private final int[] columnSums;
private final int start;
private final int end;
public ColumnSumTask(int[][] matrix, int[] columnSums, int start, int end) {
this.matrix = matrix;
this.columnSums = columnSums;
this.start = start;
this.end = end;
}
@Override
protected void compute() {
if (end - start <= 10) {
for (int j = start; j <= end; j++) {
for (int i = 0; i < matrix.length; i++) {
columnSums[j] += matrix[i][j];
}
}
} else {
int mid = (start + end) / 2;
ColumnSumTask leftTask = new ColumnSumTask(matrix, columnSums, start, mid);
ColumnSumTask rightTask = new ColumnSumTask(matrix, columnSums, mid + 1, end);
invokeAll(leftTask, rightTask);
}
}
}
private static void sortColumns(int[][] matrix, int[] columnSums) {
int cols = matrix[0].length;
int rows = matrix.length;
Integer[] columnIndices = new Integer[cols];
for (int j = 0; j < cols; j++) {
columnIndices[j] = j;
}
Arrays.sort(columnIndices, Comparator.comparingInt(j -> columnSums[j]));
int[][] sortedMatrix = new int[rows][cols];
for (int i = 0; i < rows; i++) {
for (int j = 0; j < cols; j++) {
sortedMatrix[i][j] = matrix[i][columnIndices[j]];
}
}
for (int i = 0; i < rows; i++) {
System.arraycopy(sortedMatrix[i], 0, matrix[i], 0, cols);
}
}
public static void main(String[] args) throws IOException, InterruptedException {
Scanner scanner = new Scanner(System.in);
System.out.print("Input lines: ");
int rows = scanner.nextInt();
System.out.print("Input columns: ");
int cols = scanner.nextInt();
int[][] matrix = generateMatrix(rows, cols);
writeMatrixToFile(matrix, "input_matrix.txt");
int[][] matrix1 = readMatrixFromFile("input_matrix.txt", rows, cols);
int[][] matrix2 = readMatrixFromFile("input_matrix.txt", rows, cols);
int[][] matrix3 = readMatrixFromFile("input_matrix.txt", rows, cols);
long startTime = System.currentTimeMillis();
singleThreadedSort(matrix1);
long endTime = System.currentTimeMillis();
System.out.println("One thread: " + (endTime - startTime) + " mc");
writeMatrixToFile(matrix1, "output_single_thread.txt");
startTime = System.currentTimeMillis();
multiThreadedSortWithThreadPool(matrix2, 4);
endTime = System.currentTimeMillis();
System.out.println("ThreadPoolExecutor: " + (endTime - startTime) + " mc");
writeMatrixToFile(matrix2, "output_thread_pool.txt");
startTime = System.currentTimeMillis();
multiThreadedSortWithForkJoin(matrix3);
endTime = System.currentTimeMillis();
System.out.println("ForkJoinPool: " + (endTime - startTime) + " mc");
writeMatrixToFile(matrix3, "output_fork_join.txt");
}
}