分析项目时,发现了泄漏,并将其定位到以下函数中的NSString availableStringEncodings。不知道如何修复它:
- (NSString *)stringFromArchive:(NSString *)fileName inDirectory:(NSString *)folderName
{
NSString *rStr = @"";
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *folderPath = [documentsDirectory stringByAppendingPathComponent:folderName];
NSString *filePath = [folderPath stringByAppendingPathComponent:fileName];
NSFileManager * fileManager = [NSFileManager defaultManager];
if ([fileManager fileExistsAtPath:filePath]) {
NSError *error;
const NSStringEncoding *encodings = [NSString availableStringEncodings];
NSStringEncoding encoding1;
while ((encoding1 = *encodings++) != 0)
{
rStr = [NSString stringWithContentsOfFile:filePath encoding:encoding1 error:&error];
if (rStr == nil) {
NSLog(@"error: %@", error);
}else{
break;
}
}
}
return rStr;
}发布于 2021-10-22 00:13:10
正如我们经常看到的,发现没有初始值的对象声明是很常见的,但在艰难的学习曲线中发现,我发现的许多泄漏都与简单的单元化声明实践有关……
简而言之:正确的声明也有助于调试器/工具。
NSError *error;是非常常见的。甚至会泄漏,至少仪器会觉得可疑
NSError *error = nil;更好,而且也不是NULL (这肯定会泄露)。
NSStringEncoding encoding1;
是NSUInteger的枚举,您似乎试图自下而上遍历所有编码,直到找到正确读取该文件的匹配项。然后,您可能不想从未定义的值开始,而是从1开始,这是最简单的值(NSASCIIStringEncoding)。这就是为什么要使用break;并与!=0进行比较,所以它会迭代到以零结尾的列表的末尾(还会告诉您为什么枚举不是以0开头,而是以NSASCIIStringEncoding==1开头)。
另外,当您使用const NSStringEncoding *var,然后使用*var++时,会增加什么?指针地址或存储在该地址的值..,*(var++)与(*var)++。两者都可以很好地工作,但其中一个风险更大,另一个迭代通过不存在的编码。所以猜测你想要遍历编码列表,直到它的零终止,获取值并尝试读取...
NSString *rStr = @"";
NSError *error = nil;
const NSStringEncoding *a = [NSString availableStringEncodings];
NSStringEncoding b = NSASCIIStringEncoding;
// increase addr of a, take value to b
// and check for b not 0==end-of-list
while ( (b=*(a++))!=0 ) {
//iterate until encoding allows reading successful..
rStr = [NSString stringWithContentsOfFile:@"yourfile.." encoding:b error:&error];
if (rStr != nil) break; // rStr has content, so end loop
// print reason on any missed trial
NSLog(@"error: %@", error);
}编辑:故意泄漏,只是为了好玩,如果Instruments会检测到它,我使用的泄漏代码...
extern "C" int leakingCppFunction(const char * s)
{
Example *e = new Example(s); //e is never deleted, so it leaks.
return e->getLen();
}在上面讨论的编码迭代中,清楚地发现了这个泄漏,并且没有。所以猜测你的扩展(NSStringOtherEncodings)会导致availableStringEncodings泄漏。
https://stackoverflow.com/questions/69663211
复制相似问题