正确使用 memset 与动态分配的多维数组
Posted
技术标签:
【中文标题】正确使用 memset 与动态分配的多维数组【英文标题】:Proper use of memset with dynamically allocated multidimensional arrays 【发布时间】:2014-10-30 01:13:21 【问题描述】:在循环的每次迭代中,我希望将动态定义的多维数组中的所有元素归零。
void my_function(int window_size, int row_size)
double **window_arr;
window_arr = (double **)calloc((window_size * 2), sizeof(double*));
for (i = 0; i < (window_size * 2); ++i)
window_arr[i] = (double*)calloc(3, sizeof(double));
for (i = 0; i < row_size; ++i)
...
memset(window_arr, 0, sizeof(window_arr) * (window_size * 2) * 3);
此段错误。在第一个memset
之前设置断点,但是分配之后,看起来不错。
(gdb) p window_arr[1]
$1 = (double *) 0x22604f50
(gdb) p window_arr[1][0]
$2 = 0
(gdb) q
memset
之后的断点
(gdb) p snp_window_arr[1]
$1 = (double *) 0x0
(gdb) p window_arr[1][0]
Cannot access memory at address 0x0
(gdb) q
我已经弄清楚如何将 memset 用于一维数组;我很想学习如何在上述场景中使用 memset。
【问题讨论】:
你能在第二个 calloc 之后(循环内)立即调用 memset 吗? 另外,我真的无法理解您对 memset 的使用。它的第三个参数不应该是这样的: sizeof(double) * (window_size * 2) * 3 您还假设二维数组是连续的,我不确定是否可以保证(可能)。如果没有,我的第一个建议是最安全的——分别 memset 每一行。 它不能通过将内存归零(calloc
或 memset
)来移植到零浮点变量。您应该遍历这些条目并将它们单独设置为0.0
。 (但是为什么在使用 calloc 之后还要使用 memset?calloc 已经将它返回的内存归零了。)
@ooga,因为循环的每次迭代都使用数组进行一些计算,然后需要将其归零。
【参考方案1】:
您正在构建一个指向数组的指针数组,而不是单个二维数组。这意味着您有一个指针数组,每个指针都指向一个一维数组。然后你尝试memset()
整个2D空间,但这是不可能的,因为它不是连续分配的。
您应该考虑一次为所有元素分配一个带有空间的数组,因为您的逻辑二维数组无论如何都是矩形的。只需这样做:
double *window_arr = calloc((window_size * 2) * 3, sizeof(double));
然后:
memset(window_arr, 0, (window_size * 2) * 3);
当然,您随后会将该二维数组索引为window_arr[x*window_size*2 + y]
或类似名称,而不是window_arr[x][y]
。
【讨论】:
以上是关于正确使用 memset 与动态分配的多维数组的主要内容,如果未能解决你的问题,请参考以下文章