gpt4 book ai didi

ios - 为什么有时变量在 block 中变为 NULL

转载 作者:行者123 更新时间:2023-12-01 18:06:42 25 4
gpt4 key购买 nike

我有一些来自 C++ 编写的库的事件,它在后台线程中工作:

virtual void OnData(const char* data)
{
NSLog(@"Here 'data' string is present %s", data);
@autoreleasepool {
NSString* sData= [NSString stringWithCString:data encoding:NSUTF8StringEncoding];
dispatch_async(dispatch_get_main_queue(), ^{
NSLog(@"Here _sometimes_ 'data'(%s) is nil (\0). But sData is always present %@", data, sData);
[callback OnData:sData];
});
};
}

有时我在参数变量的 dispatch_async block 中有 NULL(我怀疑它实际上是垃圾)。但是本地 NSString 变量总是在这里。为什么?

附言我真的必须使用 @autoreleasepool吗?在这个情况下?

最佳答案

您无法保证 const char *data 的缓冲区的使用生命周期。是在执行异步 block 时指向的。 data到那时可能是悬空指针(应该假设是这样)。在任何异步引用中或在它们最初创建的上下文之外使用 C 风格的指针是非常危险的。

您应该使用内存管理对象(例如 NSDataNSString 等),或者,如果您坚持使用 C 样式指针并且需要在异步 block 中引用此指针,请将数据复制到您自己的缓冲区,使用该缓冲区,然后在异步例程中使用完该缓冲区后释放它。在这种情况下,您有 sData , 所以不要引用 data在那之后,你会没事的。

附言你后来问你是否必须使用 @autoreleasepool在这个情况下。

简而言之,在大多数情况下,不需要额外的自动释放池。值得注意的是,当使用 Grand Central Dispatch(例如 dispatch_async )时,它有自己的自动释放池,因此您不必创建一个。而且,当您的主线程返回到它的运行循环时,它的池再次被耗尽。简而言之,您在实例化自己的 NSThread 时只需要手动创建自动释放池。对象。

话虽如此,如果在返回运行循环之前执行大量内存密集型操作,有时您会引入自动释放池。在这种情况下,您将添加自动释放池以减少应用程序的峰值内存使用量。但这似乎不是其中一种情况。

关于ios - 为什么有时变量在 block 中变为 NULL,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41385174/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com