Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/batch-file/6.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Xcode Can';NST数据对象的可用内存_Xcode_Memory_Garbage Collection_Nsdata_Memory Leaks - Fatal编程技术网

Xcode Can';NST数据对象的可用内存

Xcode Can';NST数据对象的可用内存,xcode,memory,garbage-collection,nsdata,memory-leaks,Xcode,Memory,Garbage Collection,Nsdata,Memory Leaks,我对xcode/cocoa甚至objective-c都是新手,因此我的问题可能很愚蠢。我正试图写一个程序,将散列文件夹中的文件。我环顾四周,找到了一种通过NSData对象加载文件的方法,然后用CC_SHA512对其字节进行散列 如果我尝试散列更多的文件,我注意到我的内存不足。使用Run->Performance工具,我可以找出我的问题。我创建的所有NSData对象仍在内存中。我尝试使用释放/解除锁定自动释放和手动释放。什么都没用 我的编译器设置是标准的,但有一个例外,我选择Objective-C

我对xcode/cocoa甚至objective-c都是新手,因此我的问题可能很愚蠢。我正试图写一个程序,将散列文件夹中的文件。我环顾四周,找到了一种通过NSData对象加载文件的方法,然后用CC_SHA512对其字节进行散列

如果我尝试散列更多的文件,我注意到我的内存不足。使用Run->Performance工具,我可以找出我的问题。我创建的所有NSData对象仍在内存中。我尝试使用释放/解除锁定自动释放和手动释放。什么都没用

我的编译器设置是标准的,但有一个例外,我选择Objective-C垃圾收集=必需

也许有人能告诉我我做错了什么

代码如下:

-(FileHash*) hashFileByName :(NSString*) filePath{

    //NSData* inputData = [inputStr dataUsingEncoding:NSUTF8StringEncoding];
    NSLog(filePath);
    NSData* inputData = [[NSData dataWithContentsOfFile:filePath] autorelease];
    unsigned char outputData[CC_SHA512_DIGEST_LENGTH];
    CC_SHA512([inputData bytes], [inputData length], outputData);


    NSMutableString* hashStr = [NSMutableString string];
    int i = 0;
    for (i = 0; i < CC_SHA512_DIGEST_LENGTH; ++i)
        [hashStr appendFormat:@"%02x", outputData[i]];


    //NSLog(@"%@ hash : %@",filePath,hashStr);

    FileHash *hash = [[[FileHash alloc]init]autorelease];
    [hash setFileHash:hashStr];
    [hash setFilePath:filePath];
    [inputdata release];
    [inputdata dealloc];
    return hash;    
}

-(NSMutableArray*) hashFilesInDirectory:(NSString*) pathToDirectory:(Boolean) recursive : (IBOutlet id) Status : (Boolean*) BreakOperation{

    NSGarbageCollector *collect = [NSGarbageCollector defaultCollector];

    NSMutableArray *files;
        files = [[self listFilesOnlyRecursive:pathToDirectory] autorelease];

    NSMutableArray *hashes = [[[NSMutableArray alloc]init]autorelease];

    for (NSString *file in files) {

        [hashes addObject: [self hashFileByName:file]]; 
        [collect collectExhaustively];
    }


    return hashes;
}

-(NSMutableArray*) listFilesOnlyRecursive : (NSString*) startDir {

    NSMutableArray *filelist = [[[NSMutableArray alloc] init]autorelease];

    //Inhalt eines Verzeichnisses auflisten (unterverzeichnisse werden ignoriert
    NSFileManager *manager = [[NSFileManager defaultManager]autorelease];

    NSDirectoryEnumerator *enumerator = [manager enumeratorAtPath:startDir];
    int count = 0;
    id file;
    while (file = [enumerator nextObject])
    {

        //      file = [[[[startDir stringByAppendingString:@"/"]autorelease] stringByAppendingString:file] autorelease
        //              ];
        file = [NSString stringWithFormat:@"%@/%@",startDir,file];
        BOOL isDirectory=NO;
        [[NSFileManager defaultManager] fileExistsAtPath:file isDirectory:&isDirectory];
        if (!isDirectory){
            [filelist addObject:file];
            //printf("\n:%s:\n",[file UTF8String]);
            count++;
        }


    }
    NSLog(@"Es waren %i files",count);
    return filelist;
}
也许有人有主意

比你提前:) Nubus有几件事:

NSData* inputData = [[NSData dataWithContentsOfFile:filePath] autorelease];
如果您想在当前方法执行之后保留它,则必须保留它(这有点过于简单,但对于您的示例来说是合理的)。由于
dataWithContentsOfFile:
不包含alloc、copy或new,除非您明确保留它,否则您不负责发布它。由于您只在函数中本地使用它,因此不需要保留它。因此,只需使用以下内容,不要调用release/autorelease或dealloc:

NSData* inputData = [NSData dataWithContentsOfFile:filePath];
此外,您从未手动解除锁定。只需根据需要释放/自动释放它们。dealloc将根据需要调用

[inputData dealloc]; // don't do this explicitly

你一定要看报纸。在阅读了记忆管理文档之后,我和以前一样了解它。所以我开始尝试出错。我尝试过释放NSData对象,直到重新计数为0。。和和。然后我找到了一个有效的解决方案

我必须自己初始化NSData对象,并将其设置为自动释放(我自己无法释放它,因为在我调用init之后,有一个2的重新绑定,尝试释放2次会导致崩溃)

布拉布拉这里是我的解决方案:

-(FileHash*) hashFileByName :(NSString*) filePath{

    NSAutoreleasePool *innerpool = [[NSAutoreleasePool alloc]init];

    //NSData* inputData = [inputStr dataUsingEncoding:NSUTF8StringEncoding];
    NSData* inputData = [[[NSData alloc]initWithContentsOfFile:filePath] autorelease];
    unsigned char outputData[CC_SHA512_DIGEST_LENGTH];
    CC_SHA512([inputData bytes], [inputData length], outputData);


    NSMutableString* hashStr = [NSMutableString string];
    int i = 0;
    for (i = 0; i < CC_SHA512_DIGEST_LENGTH; ++i)
        [hashStr appendFormat:@"%02x", outputData[i]];



    [innerpool drain];

    //NSLog(@"%@ hash : %@",filePath,hashStr);

    FileHash *hash = [[[FileHash alloc]init]autorelease];
    [hash setFileHash:hashStr];
    [hash setFilePath:filePath];

    return hash;    
}
-(FileHash*)hashFileByName:(NSString*)文件路径{
NSAutoreleasePool*innerpool=[[NSAutoreleasePool alloc]init];
//NSData*inputData=[inputStr dataUsingEncoding:NSUTF8StringEncoding];
NSData*inputData=[[[NSData alloc]initWithContentsOfFile:filePath]autorelease];
无符号字符输出数据[CC_SHA512_DIGEST_LENGTH];
CC_SHA512([inputData字节]、[inputData长度]、outputData);
NSMutableString*hashStr=[NSMutableString];
int i=0;
对于(i=0;i
我希望这会对某人有所帮助:)

谢谢你的回答


ps:也许没人能告诉我为什么我自己不能发布它,或者为什么保留计数为2

嗨,谢谢你的链接。文档说明,如果我使用方便的方法,就不必像您所说的那样使用release。NSData对象未在hashFileByName函数外部使用。我真的不知道如何摆脱NSData对象。(我没有通过文件机)有没有办法强制移除这样的物体?谢谢,方便方法会返回一个自动释放的对象。这意味着(假设其保留计数为零),它将在下一个自动释放收集点在内存中被回收。如果您想更明确地描述它,您需要alloc/init/release。
-(FileHash*) hashFileByName :(NSString*) filePath{

    NSAutoreleasePool *innerpool = [[NSAutoreleasePool alloc]init];

    //NSData* inputData = [inputStr dataUsingEncoding:NSUTF8StringEncoding];
    NSData* inputData = [[[NSData alloc]initWithContentsOfFile:filePath] autorelease];
    unsigned char outputData[CC_SHA512_DIGEST_LENGTH];
    CC_SHA512([inputData bytes], [inputData length], outputData);


    NSMutableString* hashStr = [NSMutableString string];
    int i = 0;
    for (i = 0; i < CC_SHA512_DIGEST_LENGTH; ++i)
        [hashStr appendFormat:@"%02x", outputData[i]];



    [innerpool drain];

    //NSLog(@"%@ hash : %@",filePath,hashStr);

    FileHash *hash = [[[FileHash alloc]init]autorelease];
    [hash setFileHash:hashStr];
    [hash setFilePath:filePath];

    return hash;    
}