用JAVA实现1、输于两个n×n的矩阵A和B,实现乘积运算,并输出运算结果和计算时间;2、逐渐增大矩阵A和B的规模,分析运算时间的变化。3、用分治法的实现矩阵乘积运算,比较使用分治法前后的计算量差异。
时间: 2024-05-06 09:15:18 浏览: 127
1. Java实现矩阵乘积运算代码如下:
```java
public class MatrixMultiplication {
public static void main(String[] args) {
int n = 1000; // 矩阵的维度
int[][] A = new int[n][n]; // 矩阵A
int[][] B = new int[n][n]; // 矩阵B
int[][] C = new int[n][n]; // 矩阵C
// 初始化矩阵A和B
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
A[i][j] = (int) (Math.random() * 10);
B[i][j] = (int) (Math.random() * 10);
}
}
// 计算矩阵乘积并记录运行时间
long startTime = System.currentTimeMillis();
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
for (int k = 0; k < n; k++) {
C[i][j] += A[i][k] * B[k][j];
}
}
}
long endTime = System.currentTimeMillis();
// 输出矩阵C和运行时间
System.out.println("Matrix C:");
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
System.out.print(C[i][j] + " ");
}
System.out.println();
}
System.out.println("Running time: " + (endTime - startTime) + "ms");
}
}
```
2. 逐渐增大矩阵A和B的规模,可以使用一个for循环来遍历不同维度的矩阵,并记录下运行时间,代码如下:
```java
public class MatrixMultiplication {
public static void main(String[] args) {
for (int n = 100; n <= 1000; n += 100) {
int[][] A = new int[n][n]; // 矩阵A
int[][] B = new int[n][n]; // 矩阵B
int[][] C = new int[n][n]; // 矩阵C
// 初始化矩阵A和B
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
A[i][j] = (int) (Math.random() * 10);
B[i][j] = (int) (Math.random() * 10);
}
}
// 计算矩阵乘积并记录运行时间
long startTime = System.currentTimeMillis();
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
for (int k = 0; k < n; k++) {
C[i][j] += A[i][k] * B[k][j];
}
}
}
long endTime = System.currentTimeMillis();
// 输出矩阵C和运行时间
System.out.println("Matrix size: " + n + "x" + n);
System.out.println("Running time: " + (endTime - startTime) + "ms");
}
}
}
```
3. 使用分治法实现矩阵乘积运算,可以先把矩阵分成四个子矩阵,然后递归地计算出子矩阵的乘积,最后再合并得到矩阵乘积。代码如下:
```java
public class MatrixMultiplication {
public static void main(String[] args) {
int n = 1000; // 矩阵的维度
int[][] A = new int[n][n]; // 矩阵A
int[][] B = new int[n][n]; // 矩阵B
int[][] C = new int[n][n]; // 矩阵C
// 初始化矩阵A和B
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
A[i][j] = (int) (Math.random() * 10);
B[i][j] = (int) (Math.random() * 10);
}
}
// 计算矩阵乘积并记录运行时间
long startTime = System.currentTimeMillis();
matrixMultiplication(A, B, C, 0, 0, 0, 0, n);
long endTime = System.currentTimeMillis();
// 输出矩阵C和运行时间
System.out.println("Matrix C:");
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
System.out.print(C[i][j] + " ");
}
System.out.println();
}
System.out.println("Running time: " + (endTime - startTime) + "ms");
}
// 分治法计算矩阵乘积
public static void matrixMultiplication(int[][] A, int[][] B, int[][] C, int rowA, int colA, int rowB, int colB, int size) {
if (size == 1) {
C[rowA][colB] += A[rowA][colA] * B[rowB][colB];
} else {
int newSize = size / 2;
// 计算A11和B11的乘积
matrixMultiplication(A, B, C, rowA, colA, rowB, colB, newSize);
// 计算A12和B21的乘积
matrixMultiplication(A, B, C, rowA, colA + newSize, rowB + newSize, colB, newSize);
// 计算A11和B12的乘积
matrixMultiplication(A, B, C, rowA, colA, rowB, colB + newSize, newSize);
// 计算A12和B22的乘积
matrixMultiplication(A, B, C, rowA, colA + newSize, rowB + newSize, colB + newSize, newSize);
// 计算A21和B11的乘积
matrixMultiplication(A, B, C, rowA + newSize, colA, rowB, colB, newSize);
// 计算A22和B21的乘积
matrixMultiplication(A, B, C, rowA + newSize, colA + newSize, rowB + newSize, colB, newSize);
// 计算A21和B12的乘积
matrixMultiplication(A, B, C, rowA + newSize, colA, rowB, colB + newSize, newSize);
// 计算A22和B22的乘积
matrixMultiplication(A, B, C, rowA + newSize, colA + newSize, rowB + newSize, colB + newSize, newSize);
}
}
}
```
比较使用分治法前后的计算量差异,可以在矩阵乘积运算前后分别统计矩阵乘法的次数,这里只统计乘法的次数而不计算加法的次数,代码如下:
```java
public class MatrixMultiplication {
private static int multiplyCount = 0; // 矩阵乘法次数
public static void main(String[] args) {
int n = 1000; // 矩阵的维度
int[][] A = new int[n][n]; // 矩阵A
int[][] B = new int[n][n]; // 矩阵B
int[][] C = new int[n][n]; // 矩阵C
// 初始化矩阵A和B
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
A[i][j] = (int) (Math.random() * 10);
B[i][j] = (int) (Math.random() * 10);
}
}
// 统计使用普通方法计算矩阵乘积时的乘法次数
multiplyCount = 0;
matrixMultiplication(A, B, new int[n][n], 0, 0, 0, 0, n);
System.out.println("Using normal method, multiply count: " + multiplyCount);
// 统计使用分治法计算矩阵乘积时的乘法次数
multiplyCount = 0;
divideAndConquerMultiplication(A, B, new int[n][n], 0, 0, 0, 0, n);
System.out.println("Using divide and conquer method, multiply count: " + multiplyCount);
}
// 普通方法计算矩阵乘积
public static void matrixMultiplication(int[][] A, int[][] B, int[][] C, int rowA, int colA, int rowB, int colB, int size) {
for (int i = rowA; i < rowA + size; i++) {
for (int j = colB; j < colB + size; j++) {
for (int k = colA; k < colA + size; k++) {
C[i][j] += A[i][k] * B[k][j];
multiplyCount++; // 记录乘法次数
}
}
}
}
// 分治法计算矩阵乘积
public static void divideAndConquerMultiplication(int[][] A, int[][] B, int[][] C, int rowA, int colA, int rowB, int colB, int size) {
if (size == 1) {
C[rowA][colB] += A[rowA][colA] * B[rowB][colB];
multiplyCount++; // 记录乘法次数
} else {
int newSize = size / 2;
// 计算A11和B11的乘积
divideAndConquerMultiplication(A, B, C, rowA, colA, rowB, colB, newSize);
// 计算A12和B21的乘积
divideAndConquerMultiplication(A, B, C, rowA, colA + newSize, rowB + newSize, colB, newSize);
// 计算A11和B12的乘积
divideAndConquerMultiplication(A, B, C, rowA, colA, rowB, colB + newSize, newSize);
// 计算A12和B22的乘积
divideAndConquerMultiplication(A, B, C, rowA, colA + newSize, rowB + newSize, colB + newSize, newSize);
// 计算A21和B11的乘积
divideAndConquerMultiplication(A, B, C, rowA + newSize, colA, rowB, colB, newSize);
// 计算A22和B21的乘积
divideAndConquerMultiplication(A, B, C, rowA + newSize, colA + newSize, rowB + newSize, colB, newSize);
// 计算A21和B12的乘积
divideAndConquerMultiplication(A, B, C, rowA + newSize, colA, rowB, colB + newSize, newSize);
// 计算A22和B22的乘积
divideAndConquerMultiplication(A, B, C, rowA + newSize, colA + newSize, rowB + newSize, colB + newSize, newSize);
}
}
}
```
通过对比普通方法和分治法计算矩阵乘积时的乘法次数,可以看出,使用分治法能够减少矩阵乘法的次数,从而提高矩阵乘积运算的效率。
阅读全文