2011-10-10 46 views
0

我正在使用照片選擇器來瀏覽和選擇一個視頻,一旦選擇了它,我將它從臨時存儲移到我的工作目錄中供將來使用。我這樣做是使用以下行:MoveItemAtPath帶來的內存秒殺

[[NSFileManager defaultManager] moveItemAtPath:newName toPath:newPath error:nil]; 

當我在這個過程中的內存使用高峯的視頻文件的大小,然後背下來,片刻之後輪廓的應用。有沒有辦法移動這個文件沒有內存尖峯?如果用戶的設備當時有很多應用程序正在運行,那麼我擔心我的應用程序崩潰。

如果它幫助我的路徑是這樣的: /private/var/mobile/Applications/046F9A22-DBEC-436F-936C-D59945783483/tmp//trim.PK4abv.MOV

/私營/無功/移動/Applications/046F9A22-DBEC-436F-936C-D59945783483/Documents/resources/myCards/BC742DC8-A7D4-40B8-8AC8-97CF9F242881/trim.PK4abv.MOV

回答

0

如果內存峯值與文件大小相當,則可能是它將整個文件加載到內存中,如果文件大小變得非常大,確實會造成問題。我處理這個問題的方式(複製/附加到文件時)是將文件移入小塊,像這樣(舊的C文件API):

#import <sys/stat.h> 

+(BOOL) moveFileAtPath:(NSString*)sourcePath 
      toFileAtPath:(NSString*)targetPath 
     inChunksWithSize:(size_t)bytes { 

    // open target file for appending 
    FILE *targetFile = fopen([targetPath UTF8String], "a"); 
    if(targetFile == NULL) 
     return NO; 

    FILE *sourceFile = fopen([sourcePath UTF8String], "rb"); 
    if(appendFile == NULL) { 
     fclose(targetFile); 
     return NO; 
    } 

    void *data = malloc(bytes); 
    if (data == NULL) { 
     fclose(targetFile); 
     fclose(sourceFile); 
     return NO; 
    } 

    size_t sourceSize = (size_t)filelength(fileno(sourceFile)); 
    off_t currentOffset = 0; 

    while (currentOffset < sourceSize) { 
     fseeko(sourceFile, currentOffset, SEEK_SET); 
     size_t read_bytes = fread(data, 1, bytes, sourceFile); 
     fwrite(data, 1, read_bytes, targetFile); 
     currentOffset += read_bytes; 
     if (read_bytes < 1) 
      break; 
    } 

    free(data); 
    fclose(targetFile); 
    fclose(sourceFile); 

    return YES; 
} 
+0

感謝這麼多!現在試試這個 – box86rowh

+0

如果你只是從一個移動現有的文件位置到另一個。你可以使用rename()。當源和目標位於同一個捲上時,這就是NSFileManager應該做的事情,因此我的答案是這樣。我很好奇從應用程序中看到文件系統活動輸出(帶有回溯)。 – kperryua

0

您在不同的卷「感動」?如果是這樣,那麼NSFileManager將文件複製到目的地並刪除原始文件。這個副本可能會導致你的「內存峯值」。

+0

不,我正在從臨時文件(當你選擇它們時放置視頻)和我的應用程序的文檔文件夾,這是iphone/ipad btw – box86rowh