我使用以下C ++代码进行矩阵乘法,并且在SIZE = 500时运行正常。但是当SIZE = 600或更高时代码失败。 (运行时错误)
我在Ideone.com上运行它 它输出"运行时错误时间:0内存:3292信号:11"
并且在我的本地机器中它也给了我一个错误
#include <cstdlib>
#include<iostream>
#include <stdio.h>
#include <sys/time.h>
using namespace std;
class Timer {
private:
timeval startTime;
public:
void start(){
gettimeofday(&startTime, NULL);
}
double stop(){
timeval endTime;
long seconds, useconds;
double duration;
gettimeofday(&endTime, NULL);
seconds = endTime.tv_sec - startTime.tv_sec;
useconds = endTime.tv_usec - startTime.tv_usec;
duration = seconds + useconds/1000000.0;
return duration;
}
static void printTime(double duration){
printf("%5.6f seconds\n", duration);
}
};
using namespace std;
const int SIZE = 600; // for size*size matrix
void MultiplyMatricesSequential(double a[][SIZE],double b[][SIZE],double ans[][SIZE]);
int i,j,k;
double s;
/*
*
*/
int main(int argc, char** argv) {
double a[SIZE][SIZE], b[SIZE][SIZE], ans[SIZE][SIZE];
// assign the numbers for matrix a and b
for (i = 0; i < SIZE; i++) {
for (j = 0; j < SIZE; j++) {
a[i][j]=(double)rand()/RAND_MAX;
b[i][j]=(double)rand()/RAND_MAX;
}
}
MultiplyMatricesSequential(a,b,ans);
return 0;
}
void MultiplyMatricesSequential(double a[][SIZE],double b[][SIZE],double ans[][SIZE])
{
Timer timer = Timer();
timer.start();
for (i = 0; i < SIZE; i++) {
for (j = 0; j < SIZE; j++) {
for (k = 0; k < SIZE; k++)
s += a[i][k] * b[k][j];
ans[i][j] = s;
s = 0.0;
}
}
double duration = timer.stop();
cout << "Sequential Method time elapsed for SIZE " << SIZE << " : ";
timer.printTime(duration);
}
那我在这里做错了什么?
注意: 不使用计时器时仍然是相同的。
#include <cstdlib>
#include<iostream>
#include <stdio.h>
#include <sys/time.h>
using namespace std;
const int SIZE = 500; // for size*size matrix
void MultiplyMatricesSequential(double a[][SIZE],double b[][SIZE],double ans[][SIZE]);
int i,j,k;
double s;
/*
*
*/
int main(int argc, char** argv) {
double a[SIZE][SIZE], b[SIZE][SIZE], ans[SIZE][SIZE];
// assign the numbers for matrix a and b
for (i = 0; i < SIZE; i++) {
for (j = 0; j < SIZE; j++) {
a[i][j]=(double)rand()/RAND_MAX;
b[i][j]=(double)rand()/RAND_MAX;
}
}
MultiplyMatricesSequential(a,b,ans);
return 0;
}
void MultiplyMatricesSequential(double a[][SIZE],double b[][SIZE],double ans[][SIZE])
{
for (i = 0; i < SIZE; i++) {
for (j = 0; j < SIZE; j++) {
for (k = 0; k < SIZE; k++)
s += a[i][k] * b[k][j];
ans[i][j] = s;
s = 0.0;
}
}
}
答案 0 :(得分:2)
首先 - 如果您要读取一些未知大小的数据 - 我强烈建议您使用动态内存分配来存储它,而不是预先分配一些固定大小的数组。如果这不是您的情况,或者您不想听我的建议,那么最好在全局命名空间中将更大的数组分配到堆栈中。这意味着您的代码看起来像这样:
using namespace std;
const int SIZE = 500; // for size*size matrix
void MultiplyMatricesSequential(double a[][SIZE],double b[][SIZE],double ans[][SIZE]);
int i,j,k;
double s;
/*
*
*/
double g_a[SIZE][SIZE], g_b[SIZE][SIZE], g_ans[SIZE][SIZE];
int main(int argc, char** argv) {
// assign the numbers for matrix a and b
for (i = 0; i < SIZE; i++) {
for (j = 0; j < SIZE; j++) {
g_a[i][j]=(double)rand()/RAND_MAX;
g_b[i][j]=(double)rand()/RAND_MAX;
}
}
MultiplyMatricesSequential(g_a,g_b,g_ans);
return 0;
}
//..........
请注意,我添加了一个&#34; g _&#34;你的&#34; matrices&#34;的前缀名。
也知道堆栈或&#34;本地存储&#34;用于存储临时变量和函数参数,这些参数将在调用它们所属的函数时被分配给它,并且&#34;删除&#34;什么时候回来。但是堆栈大小是固定的,如果没有空间来创建它们,程序就会崩溃。另一方面,全局变量没有内存限制,因为它们需要的空间在编译时自动分配。他们的生命周期等于应用程序运行时间作为你的&#34;矩阵&#34;是因为你已经将它们创建到&#34; main&#34;功能。所以现在的选择很简单 - 你是否想浪费程序时间分配&amp; &#34;去除&#34;数据并且还冒着堆栈溢出的风险或者没有麻烦地获取大数据 - 使用全局变量。或者如果使用真实数据 - 通过动态内存分配变得更友好。
答案 1 :(得分:0)
最重要的是,虽然600乘600的矩阵不是那么大,但堆栈内存限制(即未动态分配的变量的限制)相当低(参见例如{ {3}})。