矩阵向量相乘时出错 - 二进制操作数无效 *(有 'double *' 和 'double *')
Error in multiplying matrix vector - invalid operands to binary * (have 'double *' and 'double *')
我正在尝试使用指针将一个大的随机矩阵 (NxN) 与一个随机向量 (N) 相乘。
为什么我收到错误类型 "invalid operands to binary * (have 'double *' and 'double *')" ?
错误似乎在 ptr3[i][j] = ptr3[i] + ptr1[i] * ptr2[k];
但我不明白为什么这不起作用。
我是C的新手,所以我仍然没有得到很好的指导。
int main ()
{
time_t t;
double **ptr1, **ptr2, **ptr3;
int i, j, k;
int N = 500;
ptr1 = (double **) malloc (sizeof (double *) * N);
ptr2 = (double **) malloc (sizeof (double *) * N);
ptr3 = (double **) malloc (sizeof (double *) * N);
for (i = 0; i < N; i++)
ptr1[i] = (double *) malloc (sizeof (double) * N);
for (i = 0; i < N; i++)
ptr2[i] = (double *) malloc (sizeof (double) * N);
for (i = 0; i < N; i++)
ptr3[i] = (double *) malloc (sizeof (double) * N);
for (i = 0; i < N; i++) {
for (j = 0; j < N; j++) {
ptr1[i][j] = rand ();
}
}
for (i = 0; i < N; i++) {
*ptr2[i] = rand ();
}
t = clock();
for (i = 0; i < N; i++) {
ptr3[i] = 0;
for (k = 0; k < N; k++)
ptr3[i] = ptr3[i] + ptr1[i][k] * ptr2[k];
}
t = clock() - t;
double time_taken = ((double)t)/CLOCKS_PER_SEC;
printf("Tempo: %f segundos \n", time_taken);
printf ("\n");
return (0);
} ```
编译器说的是,在语句 ptr3[i] = ptr3[i] + ptr1[i] * ptr2[k];
中,表示 ptr1[i] * ptr2[k]
的位试图 *
在类型为 double*
的两个表达式之间.换句话说,不允许将两个指针相乘。要正确执行此操作,您需要再次取消引用([i]
和 [k]
已经将 double**
取消引用为 double*
。为了让它编译,该语句应该是(为了清楚起见我添加了括号——它们实际上并不需要):
*ptr3[i] = (*ptr3[i]) + (*ptr1[i]) * (*ptr2[k]);
这应该可以让您进行编译,但是您将 运行 遇到的下一个问题是分段错误。在你做乘法的地方上面两行,你有这个:
ptr3[i] = 0;
这是将ptr3[i]
赋值为null pointer,与C中的0
相同(其他语言对此值有不同的名称:null
, None
, 等等)。我想你在这里的意思是:
*ptr3[i] = 0;
顺便说一句,由于 N
是一个已知的固定值,您可以选择不处理所有 malloc
内容,只需说:
const int N = 500;
double ptr1[N][N];
double ptr2[N][N];
// ... and so on ...
这是将 ptr1
声明为 数组 而不是指针,这在内存访问模式方面与指针相同,但是 different in a number of ways .根据您要学习的内容,不处理动态内存(使用 malloc
和 free
)现在可能会让您省去一些麻烦。
我正在尝试使用指针将一个大的随机矩阵 (NxN) 与一个随机向量 (N) 相乘。 为什么我收到错误类型 "invalid operands to binary * (have 'double *' and 'double *')" ? 错误似乎在 ptr3[i][j] = ptr3[i] + ptr1[i] * ptr2[k]; 但我不明白为什么这不起作用。 我是C的新手,所以我仍然没有得到很好的指导。
int main ()
{
time_t t;
double **ptr1, **ptr2, **ptr3;
int i, j, k;
int N = 500;
ptr1 = (double **) malloc (sizeof (double *) * N);
ptr2 = (double **) malloc (sizeof (double *) * N);
ptr3 = (double **) malloc (sizeof (double *) * N);
for (i = 0; i < N; i++)
ptr1[i] = (double *) malloc (sizeof (double) * N);
for (i = 0; i < N; i++)
ptr2[i] = (double *) malloc (sizeof (double) * N);
for (i = 0; i < N; i++)
ptr3[i] = (double *) malloc (sizeof (double) * N);
for (i = 0; i < N; i++) {
for (j = 0; j < N; j++) {
ptr1[i][j] = rand ();
}
}
for (i = 0; i < N; i++) {
*ptr2[i] = rand ();
}
t = clock();
for (i = 0; i < N; i++) {
ptr3[i] = 0;
for (k = 0; k < N; k++)
ptr3[i] = ptr3[i] + ptr1[i][k] * ptr2[k];
}
t = clock() - t;
double time_taken = ((double)t)/CLOCKS_PER_SEC;
printf("Tempo: %f segundos \n", time_taken);
printf ("\n");
return (0);
} ```
编译器说的是,在语句 ptr3[i] = ptr3[i] + ptr1[i] * ptr2[k];
中,表示 ptr1[i] * ptr2[k]
的位试图 *
在类型为 double*
的两个表达式之间.换句话说,不允许将两个指针相乘。要正确执行此操作,您需要再次取消引用([i]
和 [k]
已经将 double**
取消引用为 double*
。为了让它编译,该语句应该是(为了清楚起见我添加了括号——它们实际上并不需要):
*ptr3[i] = (*ptr3[i]) + (*ptr1[i]) * (*ptr2[k]);
这应该可以让您进行编译,但是您将 运行 遇到的下一个问题是分段错误。在你做乘法的地方上面两行,你有这个:
ptr3[i] = 0;
这是将ptr3[i]
赋值为null pointer,与C中的0
相同(其他语言对此值有不同的名称:null
, None
, 等等)。我想你在这里的意思是:
*ptr3[i] = 0;
顺便说一句,由于 N
是一个已知的固定值,您可以选择不处理所有 malloc
内容,只需说:
const int N = 500;
double ptr1[N][N];
double ptr2[N][N];
// ... and so on ...
这是将 ptr1
声明为 数组 而不是指针,这在内存访问模式方面与指针相同,但是 different in a number of ways .根据您要学习的内容,不处理动态内存(使用 malloc
和 free
)现在可能会让您省去一些麻烦。