2009-12-28 118 views
0

我想拆分執行查詢。下面的myprepare函數打開數據庫連接並運行sqlite3_prepare_v2函數。在myprepare的作用域內執行sqlite3_open後,selectstmt和database將爲其分配有效地址。但是,一旦我從myprepare出來,他們的地址被擦除爲0x0。傳入變量的值不保留

sqlite3_stmt *selectstmt = nil; 
sqlite3 *database = nil; 

[anInstance myprepare:selectstmt theDatabase:database]; //assignments are fine inside here 

//here, the above values will be 0x0 

爲什麼selectstmt和database的值不保留在myprepare之外?

+0

對於那些誰不想花5分鐘時間撓頭:「保留」在這個意義上並不是與內存管理有關,而應該是「變量中傳遞的值不被保留」。 – 2009-12-28 22:40:58

回答

7

selectstmtdatabase是指向對象的指針。如果你想要一個函數來影響指針的值(而不是它指向的對象),你必須通過引用來傳遞它們。換句話說,myprepare:theDatabase:將不得不原型如下:

- (void)myPrepare:(sqlite3_stmt **)selectstmt theDatabase:(sqlite3 **)database; 

而且你將不得不調用它像這樣:

[anInstance myprepare:&selectstmt theDatabase:&database]; 

你傳遞一個指針的指針這樣的話,你可以通過取消引用方法中的參數來更改指針的值。

你的數據庫包裝對象,真的應該被跟蹤數據庫的內部處理,你應該回傳的值作爲返回值,因爲它幾乎總是比參考清潔:

MyClass *anInstance = [[MyClass alloc] initAndOpenDatabase]; 

sqlite3_stmt *selectstmt = [anInstance prepareStatement]; 

... 

[anInstance close]; 
[anInstance release];