2010-08-13 38 views
0

我在回調函數中給出了一些數據以順序寫入磁盤,每0.02秒約4KB。如果我從回調函數所在的線程中獲得fwrite(),則在同一個線程中的其他代碼段中會出現一些滯後現象。所以爲了在寫入磁盤時不阻塞這個線程,我想將fwrite代碼移動到另一個線程。問題在於回調函數沒有實例範圍,所以我僅限於調用靜態函數或類方法。我想寫的數據屬於實例。如何在單獨的線程中執行順序文件寫入

我有什麼選擇?我試着用NSOperationQueue塊:

void (^ioBlock)(void) = ^{ 
     fwrite(saveBuffer, length * 4, 1, file); 
    }; 
FileSaveOperation *op = [[FileSaveOperation alloc] initWithBlock:ioBlock]; 
    [opQueue addOperation:op]; 
    [op release]; 

在FileSaveOperation我成立了池:

- (void)main 
{ 
    NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; 
    [NSRunLoop currentRunLoop]; 
    block(); 

    [pool release]; 


} 

但是這給了我這個錯誤:

_NSAutoreleaseNoPool():對象0x33ad20類__NSFastEnumerationEnumerator的autoreleased沒有到位的地方 - 只是漏水

我不能使用performSelector:onThread:,因爲我無法訪問該實例。我應該讓我的數據成員是靜態的嗎?有更好的解決方案嗎?

+0

你的回調函數沒有上下文參數來傳遞你的實例? – Nyx0uf 2010-08-13 12:40:55

回答

2

如果您不擔心早於iOS 4.0的支持,請查看Grand Central Dispatch。您可以使塊或函數指針與其中捕獲的上下文內聯。然後,您使用GCD創建一個新的隊列,它將爲您處理所有線程。一旦完成,只需要做任何你想要的塊調用。

所有塊都記住它們的創建位置的上下文。使用GCD的最佳示例可以在WWDC視頻的核心操作系統部分找到。

這是我用來完成幾乎所有線程工作的方法。