小森最近在工作上遇到了一些麻烦,他需要在许多矩阵上计算卷积的结果,希望你能够帮助他写一个程序简化计算。
小森已经将他要计算的卷积处理成了如下的简化形式,以便即使不了解卷积的人也可以进行计算:
给出一个n*m的矩阵A和一个3*3的矩阵B,A和B的计算结果是一个(n-2)*(m-2)的矩阵C,满足:
请按照以上公式,根据给出的矩阵A和B计算出矩阵C。
输入的第一行为两个正整数n和m,其中3 <= n, m <= 500。接下来的n行,每行包含m个用空格分隔的整数,其中第x行第y列的整数为,且。接下来的3行,每行包含3个用空格分隔的整数,其中第x行第y列的整数为,且。
输出包含n-2行,每行包含m-2个用空格分隔的整数,其中第x行第y列的整数为。
4 4 1 2 3 4 5 4 3 2 -1 -2 -3 -4 -5 -4 -3 -2 1 0 -1 0 -1 1 -1 0 1
-5 -5 3 3
以输出样例中左上角的-5为例:
(1 * 1) + (2 * 0) + (3 * (-1)) + (5 * 0) + (4 * (-1)) + (3 * 1) + ((-1) * (-1)) + ((-2) * 0) + ((-3) * 1) = 1 + 0 + (-3) + 0 + (-4) + 3 + 1 + 0 + (-3) = -5
#include <stdio.h> #include <stdlib.h> #define N 500 int n, m; int feat[N][N]; int kernel[3][3]; int main() { scanf("%d %d",&n, &m); for(int i=0; i<n; i++){ for(int j=0; j<m; j++){ scanf("%d", &feat[i][j]); } } for(int i=0; i<3; i++){ for(int j=0; j<3; j++){ scanf("%d", &kernel[i][j]); } } int res[N][N]; int sum; for(int i=0; i<n-2; i++){ for(int j=0; j<m-2; j++){ // int sum = 0; 运行时间 83ms 占用内存 4848KB // 循环外int sum; 这里sum=0; 运行时间 82ms 占用内存 4904KB, 避免了重复定义的时间,但是每次都需要开辟一块内存,且在并行计算时,如果多个线程同时访问同一个变量,可能会导致数据竞争的问题,需要使用同步机制来保证数据的正确性 int sum = 0; for(int k=0; k<3; k++){ for(int l=0; l<3; l++){ sum += feat[i+k][j+l] * kernel[k][l]; } } res[i][j] = sum; } } // 在循环中输出会导致程序频繁地调用输出函数,增加了 I/O 操作的次数,从而影响程序的效率。因此,在循环外面先计算好结果,再一次性输出,可以减少 I/O 操作的次数,提高程序的效率。 for(int i=0; i<n-2; i++){ for(int j=0; j<m-2; j++){ printf("%d ",res[i][j]); } printf("\n"); } return 0; }
import java.util.*; public class Main { public static void main(String[] args) { Scanner in = new Scanner(System.in); int n = in.nextInt(), m = in.nextInt(); int[][] a = new int[n][m]; int[][] b = new int[3][3]; for (int i = 0; i < n; i++) { for (int j = 0; j < m; j++) { a[i][j] = in.nextInt(); } } for (int i = 0; i < 3; i++) { for (int j = 0; j < 3; j++) { b[i][j] = in.nextInt(); } } for (int i = 0; i < n-2; i++) { for (int j = 0; j < m-2; j++) { int sum = 0; for (int k = 0; k < 3; k++) { for (int l = 0; l < 3; l++) { sum += a[i + k][j + l] * b[k][l]; } } if (j == m-3) System.out.println(sum); else System.out.print(sum + " "); } } } }
#include <iostream> using namespace std; int main() { int n,m; cin>>n>>m; int matrix[n][m]; for(int i=0;i<n;i++) { for(int j=0;j<m;j++) { cin>>matrix[i][j]; } } int kernl[3][3]; for(int i=0;i<3;i++) { for(int j=0;j<3;j++) { cin>>kernl[i][j]; } } for(int i=0;i<n-2;i++) { for(int j=0;j<m-2;j++) { int res=0; for(int k=0;k<=2;k++) { for(int l=0;l<=2;l++) { res+=matrix[i+k][j+l]*kernl[k][l]; } } cout<<res<<" "; } cout<<endl; } return 0; }