天天看點

IOS學習筆記28—SQLite3第三方庫之FMDB

SQLite是一種小型的輕量級的關系型資料庫,在移動裝置上使用是非常好的選擇,無論是Android還是IOS,都内置了SQLite資料庫,現在的版本都是SQLite3。在IOS中使用SQLite如果使用SDK提供的方法,特别麻煩也不利于了解和使用,在之前的http://blog.csdn.net/tangren03/article/details/7781930文章中就是使用IOS的SDK自帶的SQLite API來使用資料庫,感覺使用很不友善,今天就講講一個針對IOS的SQlite API封裝的第三方庫FMDB,FMDB對SDK中的API做了一層封裝,使之使用OC來通路,使用友善而且更熟悉。FMDB的下載下傳位址https://github.com/ccgus/fmdb。

FMDB主要涉及兩個類,FMDatabase和FMResultSet,前者類似于Android中的SQLiteOpenHelper或SQLiteDatabase,FMResultSet類似于Android中的Cursor,用來存儲結果集。

下載下傳完FMDB源碼後把檔案拖到工程中,并導入SQLite支援庫,工程目錄如下:

IOS學習筆記28—SQLite3第三方庫之FMDB

然後就是這個Demo的完整截圖:

IOS學習筆記28—SQLite3第三方庫之FMDB

然後就來看看如何操作FMDB:

//點選按鈕後執行儲存到資料庫的操作
- (IBAction)saveButtonClicked:(id)sender {
    //擷取Document檔案夾下的資料庫檔案,沒有則建立
    NSString *docPath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) objectAtIndex:0];
    NSString *dbPath = [docPath stringByAppendingPathComponent:@"user.db"];
    
    //擷取資料庫并打開
    FMDatabase *database  = [FMDatabase databaseWithPath:dbPath];
    if (![database open]) {
        NSLog(@"Open database failed");
        return;
    }
    
    //建立表(FMDB中隻有update和query操作,出了查詢其他都是update操作)
    [database executeUpdate:@"create table user (name text,gender text,age integer)"];
    
    //插入資料
    BOOL insert = [database executeUpdate:@"insert into user values (?,?,?)",nameTextField.text,genderTextField.text,ageTextField.text];
    
    if (insert) {
        UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"提示" message:@"儲存成功" delegate:self cancelButtonTitle:@"确定" otherButtonTitles:nil, nil];
        [alert show];
        [alert release];
    }
    
    [database close];
}
           

操作成功後彈出提示框:

IOS學習筆記28—SQLite3第三方庫之FMDB
//點選按鈕後執行查詢操作
- (IBAction)queryButtonTapped:(id)sender {
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *documentPath = [paths objectAtIndex:0];
    NSString *dbPath = [documentPath stringByAppendingPathComponent:@"user.db"];
    
    FMDatabase *database = [FMDatabase databaseWithPath:dbPath];
    if (![database open]) {
        return;
    }
    
    //不需要像Android中那樣關閉Cursor關閉FMResultSet,因為相關的資料庫關閉時,FMResultSet也會被自動關閉
    FMResultSet *resultSet = [database executeQuery:@"select * from user"];
    while ([resultSet next]) {
        NSString *name = [resultSet stringForColumn:@"name"];
        NSString *gender = [resultSet stringForColumn:@"gender"];
        int age = [resultSet intForColumn:@"age"];
        NSLog(@"Name:%@,Gender:%@,Age:%d",name,gender,age);
        
    }
    
    [database close];
    //這裡也不需要release
//    [database release];
}
           
IOS學習筆記28—SQLite3第三方庫之FMDB

FMResultSet還支援以下方式擷取值:

  • intForColumn:

  • longForColumn:

  • longLongIntForColumn:

  • boolForColumn:

  • doubleForColumn:

  • stringForColumn:

  • dateForColumn:

  • dataForColumn:

  • dataNoCopyForColumn:

  • UTF8StringForColumnIndex:

  • objectForColumn:

//執行條件查詢操作
- (IBAction)queryByConditionBtnTapped:(id)sender {
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *docPath = [paths objectAtIndex:0];
    NSString *dbPath = [docPath stringByAppendingPathComponent:@"user.db"];
    
    FMDatabase *database = [FMDatabase databaseWithPath:dbPath];
    if (![database open]) {
        return;
    }
    
    FMResultSet *resultSet = [database executeQuery:@"select * from user where name = ?",@"Ryan"];
    while ([resultSet next]) {
        NSString *name = [resultSet stringForColumn:@"name"];
        NSString *gender = [resultSet stringForColumn:@"gender"];
        int age = [resultSet intForColumn:@"age"];
        NSLog(@"Name:%@,Gender:%@,Age:%d",name,gender,age);
    }
    
    [database close];
}
           
IOS學習筆記28—SQLite3第三方庫之FMDB
//執行更新操作
- (IBAction)updateBtnTapped:(id)sender {
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *docPath = [paths objectAtIndex:0];
    NSString *dbPath = [docPath stringByAppendingPathComponent:@"user.db"];
    
    FMDatabase *database = [FMDatabase databaseWithPath:dbPath];
    if (![database open]) {
        return;
    }
    
    //參數必須是NSObject的子類,int,double,bool這種基本類型,需要封裝成對應的包裝類才可以
    BOOL update = [database executeUpdate:@"update user set name = ? where age = ?",@"RyanTang",[NSNumber numberWithInt:24]];

    if(update){
        UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"提示" message:@"更新成功" delegate:self cancelButtonTitle:@"确定" otherButtonTitles:nil, nil];
        [alert show];
        [alert release];
    }

    [database close];
}
           
IOS學習筆記28—SQLite3第三方庫之FMDB
//執行删除操作
- (IBAction)deleteBtnTapped:(id)sender {
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *docPath = [paths objectAtIndex:0];
    NSString *dbPath = [docPath stringByAppendingPathComponent:@"user.db"];
    
    FMDatabase *database = [FMDatabase databaseWithPath:dbPath];
    if (![database open]) {
        return;
    }

    BOOL delete = [database executeUpdate:@"delete from user where name = ?",@"Tang"];
    if (delete) {
        UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"提示" message:@"删除成功" delegate:self cancelButtonTitle:@"确定" otherButtonTitles:nil, nil];
        [alert show];
        [alert release];

    }
    
    [database close];
}
           
IOS學習筆記28—SQLite3第三方庫之FMDB

如果我們的app需要多線程操作資料庫,那麼就需要使用FMDatabaseQueue來保證線程安全了。切記不能在多個線程中共同一個FMDatabase對象并且在多個線程中同時使用,這個類本身不是線程安全的,這樣使用會造成資料混亂等問題。

     使用FMDatabaseQueue很簡單,首先用一個資料庫檔案位址來初使化FMDatabaseQueue,然後就可以将一個閉包(block)傳入inDatabase方法中。在閉包中操作資料庫,而不直接參與FMDatabase的管理。

-(void)executeDBOperation
{
    //擷取Document檔案夾下的資料庫檔案,沒有則建立
    NSString *docPath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) objectAtIndex:0];
    NSString *dbPath = [docPath stringByAppendingPathComponent:@"user.db"];
    
    FMDatabaseQueue *databaseQueue = [FMDatabaseQueue databaseQueueWithPath:dbPath];
    [databaseQueue inDatabase:^(FMDatabase *db){
    [db executeUpdate:@"insert into user values (?,?,?)",@"Ren",@"Male",[NSNumber numberWithInt:20]];
    }];
    [databaseQueue close];
}
           

工程源碼:下載下傳

加入我們的QQ群或微信公衆賬号請檢視: Ryan's zone公衆賬号及QQ群

歡迎關注我的新浪微網誌和我交流:@唐韌_Ryan