1

我正在使用 libical 库来解析 iCalendar 格式并从中读取我需要的信息。到目前为止,它工作得非常好,但是关于 ical 有一件奇怪的事情。这是我的代码:

icalcomponent *root = icalparser_parse_string([iCalData cStringUsingEncoding:NSUTF8StringEncoding]);

if (root)
{    
    icalcomponent *currentEvent = icalcomponent_get_first_component(root, ICAL_VEVENT_COMPONENT);

    while (currentEvent)
    {    
        while(currentProperty)
        {    
            icalvalue *value = icalproperty_get_value(currentProperty);
            char *icalString = icalvalue_as_ical_string_r(value); //seems to leak
            NSString *currentValueAsString = [NSString stringWithCString:icalString
                                                                encoding:NSUTF8StringEncoding];
            icalvalue_free(value);
            //...
            //import data
            //...
            icalString = nil;
            currentValueAsString = nil;
            icalproperty_free(currentProperty);
            currentProperty = icalcomponent_get_next_property(currentEvent, ICAL_ANY_PROPERTY);
        } //end while
    } //end while
    icalcomponent_free(currentEvent);
}
icalcomponent_free(root);

//...

我确实使用了工具来检查我的内存使用情况,并且能够发现这条线似乎泄漏了:

char *icalString = icalvalue_as_ical_string_r(value); //seems to leak

如果我将此行复制并粘贴 5 或 6 次,我的内存使用量将增长约 400kb,并且再也不会被释放。

该方法没有免费方法,icalvalue_as_ical_string_r因为它返回一个 char *..

任何建议如何解决这个问题?我将不胜感激任何帮助!

编辑

看一下苹果文档说以下内容:

要从字符串对象中获取 C 字符串,建议使用 UTF8String。这将返回一个使用 UTF8 字符串编码的 const char *。

const char *cString = [@"Hello, world" UTF8String];

您收到的 C 字符串归一个临时对象所有,并且在发生自动解除分配时将变为无效。如果要获取永久的 C 字符串,则必须创建一个缓冲区并复制该方法返回的 const char * 的内容。

但是如果使用 arc,现在如何正确释放 char * 字符串?我试图在我的while循环前面添加@autorelease {...},但没有任何努力。仍在增加内存使用...

4

2 回答 2

1

icalvalue_as_ical_string_r返回 achar *因为它为您的结果字符串执行了 malloc() 。如果您的指针非 NULL,则必须在使用后对其进行 free()。

于 2012-07-16T14:26:18.663 回答
1

小心声明“没有免费方法......因为它返回一个 char*”;这绝不是您可以假设的事情。

在没有文档的情况下,您可以查看库的源代码以了解它的作用;例如:

http://libical.sourcearchive.com/documentation/0.44-2/icalvalue_8c-source.html

不幸的是,这个函数可以做很多不同的事情。当然,在某些情况下调用free()返回的缓冲区是正确的,但也许并非在每种情况下都可以确保这一点。

我认为最好从库的维护者那里请求一个适当的释放方法。他们需要收拾自己的烂摊子;该icalvalue_as_ical_string_r()函数至少有十几个switch可能具有不同释放要求的情况。

于 2012-07-16T14:31:06.543 回答