在 C 中使用清理属性释放二维数组的通用函数
Generic function to free 2d arrays with cleanup attribute in C
我最近发现 __attribute__((cleanup))
这非常方便。我做了一个通用函数来释放任何类型的指针,它工作正常。
#define _autofree_ __attribute__ ((cleanup(free_pointer)))
...
void free_pointer(void *pointer)
{
free(*(void **) pointer);
}
但在释放二维数组时并不那么容易。据我所知,出于堆栈限制的原因,清理使用指向给定指针的指针,这是一件好事,因为它在任何时候都不使用它的 copy 。无论如何,取消引用 (void **)
强制转换以通过 "derefencing void *" 错误是可行的,但是如果我这样做了
#define _autofree2d_ __attribute__ ((cleanup(free_pointer_array)))
...
void free_pointer_array(void *pointer_array)
{
for (size_t i = 0 ; (void **) pointer_array[i] ; ++i)
free(*(void **) pointer_array[i]);
free(*(void ***) pointer_array);
}
由于括号 [i]
,我最终取消了对 void * 的引用。这看起来也不对。
我也在尝试使用 char 指针以一种不太通用的方式来完成它(因为我目前正在使用一个字数组)并且它编译但由于无效的空闲给我们一个段错误。
void free_pointer_array(char ***array)
{
for (size_t i = 0 ; *array[i] ; ++i)
free(*array[i]);
free(**array); // Tried using ***array and got
// "pointer from integer without a cast" error
}
正如 Andrew Henle 在评论中提到的,我的分配方法有问题。我正在做一个 查找 table 而不是实际的二维数组。使用此处描述的方法:,我可以简单地将我原来的 _autofree_
宏用于任何维度的数组。
我最近发现 __attribute__((cleanup))
这非常方便。我做了一个通用函数来释放任何类型的指针,它工作正常。
#define _autofree_ __attribute__ ((cleanup(free_pointer)))
...
void free_pointer(void *pointer)
{
free(*(void **) pointer);
}
但在释放二维数组时并不那么容易。据我所知,出于堆栈限制的原因,清理使用指向给定指针的指针,这是一件好事,因为它在任何时候都不使用它的 copy 。无论如何,取消引用 (void **)
强制转换以通过 "derefencing void *" 错误是可行的,但是如果我这样做了
#define _autofree2d_ __attribute__ ((cleanup(free_pointer_array)))
...
void free_pointer_array(void *pointer_array)
{
for (size_t i = 0 ; (void **) pointer_array[i] ; ++i)
free(*(void **) pointer_array[i]);
free(*(void ***) pointer_array);
}
由于括号 [i]
,我最终取消了对 void * 的引用。这看起来也不对。
我也在尝试使用 char 指针以一种不太通用的方式来完成它(因为我目前正在使用一个字数组)并且它编译但由于无效的空闲给我们一个段错误。
void free_pointer_array(char ***array)
{
for (size_t i = 0 ; *array[i] ; ++i)
free(*array[i]);
free(**array); // Tried using ***array and got
// "pointer from integer without a cast" error
}
正如 Andrew Henle 在评论中提到的,我的分配方法有问题。我正在做一个 查找 table 而不是实际的二维数组。使用此处描述的方法:_autofree_
宏用于任何维度的数组。