我是C编程的新手,这类事情不断涌现。作为一个简单的例子,假设我有一个带有一些指针的struct http_header
:
struct http_header {
char* name;
char* value;
};
我想填充一个
char
,其中http_header
是一个int的字符串表示。从语义上讲,我“感觉”像是,我应该能够编写一个函数,它接受一个空的头指针、一个名称字符串和一个value
,并适当地填充头。void fill_header(struct http_header *h, char* name, int value)
{
h->name = name;
char *value_str = malloc(100);
sprintf(value_str, "%d", value);
h->value = value_str;
}
int main(int argc, const char * argv[])
{
struct http_header h;
char *name = "Header Name";
int val = 42;
fill_header(&h, name, val);
...
free(h.value);
}
在这里,调用代码的读取与我的意图完全一致,但在本例中,我正在动态创建
int
字符串,这意味着我以后必须释放它。我觉得这不太对劲;似乎调用者对value
的实现了解得太多了。在实际实现中,可能不太容易知道要释放什么:考虑填充一个fill_header
s数组,其中只有一个数组需要其值http_header
ed。为了解决这个问题,我必须事先创建字符串:
void fill_header2(struct http_header *h, char* name, char *value_str)
{
h->name = name;
h->value = value_str;
}
int main(int argc, const char * argv[])
{
struct http_header h;
char *name = "Header Name";
int value = 42;
char value_str[100];
sprintf(value_str, "%d", value);
fill_header2(&h, name, value_str);
}
随着这种模式在结构链中的延续,并指向其他结构,我最终在顶级函数中做了很多工作,而低级函数似乎不值得这么做。此外,我基本上已经牺牲了“用
malloc
填充头”的想法,这是我开始写的。我是不是少了点什么?是否有一些模式或设计选择可以让我的生活更轻松,并保持我的函数调用表达我的意图?感谢Stackoverfow的所有人,他们是我有过的最好的教授。
最佳答案
好吧,我将使用第一种方法(一种扭曲),并提供一个destroy
函数:
struct http_header *make_header(char *name, int value)
{
struct http_header *h = malloc(sizeof *h);
/* ... */
return h;
}
void destroy_header(struct http_header *h)
{
free(h->name);
free(h);
}
这样,来电者就不必知道任何关于
http_header
的信息。您还可以使用一个将主分配(结构本身)留给调用者并自己进行内部分配的版本。然后您必须提供一个
clear_header
它只释放分配的fill
资源。但这会给你留下一个部分有效的对象。