美文网首页
iOS持久化方案

iOS持久化方案

作者: 简洁的想法 | 来源:发表于2017-05-19 09:45 被阅读28次

    iOS常用的数据持久化方案主要有四种:NSUserDefault、File、Keychain、FMDB。

    NSUserDefaults

    model

    student.h

    #import <Foundation/Foundation.h>
    
    @interface student : NSObject <NSCoding>
    
    @property (nonatomic, strong) NSNumber *number;
    @property (nonatomic, strong) NSString *sex;
    @property (nonatomic, strong) NSString *name;
    @property (nonatomic, strong) NSNumber *age;
    
    
    @end
    

    student.m

    #import "student.h"
    
    @implementation student
    
    
    - (instancetype)init
    {
        self = [super init];
        if (self) {
    //        _number = @(1);
            _name = @"zhiajf";
            _age = @(2763);
            _sex = @"男";
        }
        return self;
    }
    
    
    
    /* 
     编码器
     Encodes the receiver using a given archiver(归档器).
     */
    - (void)encodeWithCoder:(NSCoder *)aCoder
    {
        [aCoder encodeObject:self.number forKey:@"number"];
        [aCoder encodeObject:self.name forKey:@"name"];
        [aCoder encodeObject:self.age forKey:@"age"];
        [aCoder encodeObject:self.sex forKey:@"sex"];
    }
    
    
    /*
     译码器
     Returns an object initialized from data in a given unarchiver(取档器).
     You typically return self from initWithCoder:. If you have an advanced need that requires substituting a different object after decoding, you can do so in awakeAfterUsingCoder:.
     */
    - (nullable instancetype)initWithCoder:(NSCoder *)aDecoder
    {
        self.number = [aDecoder decodeObjectForKey:@"number"];
        self.name = [aDecoder decodeObjectForKey:@"name"];
        self.age = [aDecoder decodeObjectForKey:@"age"];
        self.sex = [aDecoder decodeObjectForKey:@"sex"];
        return self;
    }
    
    @end
    
        NSLog(@"****%@****",[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject]);
    
        
        student *aStudent = [[student alloc] init];
        aStudent.number = @1;
        
        student *aStudent2 = [[student alloc] init];
        aStudent2.number = @2;
        aStudent2.name = @"第二个stu";
        
        /*********************** NSUserDefault **********************/
        
        NSData *data = [NSKeyedArchiver archivedDataWithRootObject:aStudent];
       
        [[NSUserDefaults standardUserDefaults] setObject:data forKey:@"student"];
        NSData *studentData = [[NSUserDefaults standardUserDefaults] objectForKey:@"student"];
        
        student *studentModel = [NSKeyedUnarchiver unarchiveObjectWithData:studentData];
        
        NSLog(@"****%@****",studentModel.sex);
    

    File

    /*********************** file **********************/
        
        NSString *path =  [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
        path = [path stringByAppendingString:@"/my.archive"];
        
        NSArray *array = @[aStudent,aStudent2];
        
        [NSKeyedArchiver archiveRootObject:array toFile:path];
        NSArray *array2 = [NSKeyedUnarchiver unarchiveObjectWithFile:path];
        /*
         [NSKeyedArchiver archiveRootObject:aStudent toFile:path];
         student *stuArchiver = [NSKeyedUnarchiver unarchiveObjectWithFile:path];
     
         [NSKeyedArchiver archiveRootObject:aStudent2 toFile:path];
         student *stuArchiver2 = [NSKeyedUnarchiver unarchiveObjectWithFile:path];
         */
        student *stuArchiver = array2[0];
        student *stuArchiver2 = array2[1];
        
    //    NSLog(@"****%@****",stuArchiver.name);
    //    NSLog(@"****%@****",stuArchiver2.name);
    

    Keychain

    /*********************** keychain **********************/
        /*
         参考
         http://www.jianshu.com/p/9188235eedab
         https://github.com/v2panda/PDKeyChain
         */
    

    FMDB

        // 创建db
        NSString *path =  [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
        NSLog(@"****%@****",path);
        
        
        path = [path stringByAppendingString:@"/User.db"];
        
        //实例化一个FMDatabase对象,并打开一个数据库,如果没有这个数据库,就会创建一个数据库
        FMDatabase *db = [FMDatabase databaseWithPath:path];
        
        // 打开db
        [db open];
        if(![db open]) {
            return;
        }
        // 增删改查
        /*
         create\update\insert\alter\begin\detach
         
         */
        
        
        
        //创建表
        [db executeUpdate:@"CREATE TABLE Users(Name text,Age integer)"];
        
        
        //插入数据
        [db executeUpdate:@"INSERT INTO Users(Name,Age)VALUES(?,?)",@"Eric",[NSNumber numberWithInt:25]];
        
        
        NSString *userName1 = [db stringForQuery:@"SELECT Name FROM Users WHERE Age = ?",@"25"];
        
        NSLog(@"%@", userName1);
        
       
        
        // 更新数据
        [db executeUpdate:@"UPDATE Users SET Name = ? WHERE Name = ?",@"Michael",@"Eric"];
        NSLog(@"%@", userName1);
        
        
        
        //删除数据
        [db executeUpdate:@"DELETE FROM Users WHERE Name = ?",@"Michael"];
        
        
        
        //查询数据
        NSString *userName = [db stringForQuery:@"SELECT Name FROM Users WHERE Age = ?",@"25"];
        NSLog(@"%@", userName);
        
        
        //查询多个数据,FMResultSet类,是一个结果集,返回多条数据,FMDB会将数据放在这个结果集中,然后在对这个结果集进行查询即可
        FMResultSet *res = [db executeQuery:@"SELECT * FROM Users"];
        res = [db executeQuery:@"SELECT * FROM Users WHERE Age = ?",@"25"];
        while ([res next]) {
            NSString *name = [res stringForColumn:@"Name"];
            
            NSString *age = [res stringForColumn:@"Age"];
            NSLog(@"%@%@", name, age);
        }
        
        
        // 关闭db
        [db close];
    
    // 使用FMDatabaseQueue类实现多线程操作
        
        FMDatabaseQueue *queue = [FMDatabaseQueue databaseQueueWithPath:fileName];
        [queue inDatabase:^(FMDatabase *db) {
            
            [db executeUpdate:@"create table if not exists t_student_q (id integer primary key autoincrement, name text not null, age integer not null)"];
            
            int age = 42;
            NSString *name = @"name 1";
            
            //1.executeUpdate:不确定的参数用?来占位(后面参数必须是oc对象,;代表语句结束)
            [db executeUpdate:@"INSERT INTO t_student_q (name, age) VALUES (?,?);",name,@(age)];
            
            FMResultSet *rs = [db executeQuery:@"select * from t_student_q"];
            
            while([rs next]) {
                NSString *name = [rs objectForColumnName:@"name"];
    
                NSLog(@"****%@==****",name);
            }
        }];
    

    参考
    FMDB
    FMDB多线程安全问题

    相关文章

      网友评论

          本文标题:iOS持久化方案

          本文链接:https://www.haomeiwen.com/subject/ifdibttx.html