zoukankan      html  css  js  c++  java
  • (一一五)利用NSKeyedArchiver实现任意对象转为二进制

    【应用背景】

    在数据库中存储数据时,如果对象过于复杂,又不必要创建复杂的表,可以直接把整个对象转化为二进制存入数据库字段,然后取出后再还原即可。

    【实现方法】

    在PHP中,使用序列化和反序列化可以实现这样的功能。

    在OC中,使用NSKeyedArchiver和NSKedUnarchiver可以实现对象转二进制和二进制转对象,要实现转化,必须遵循NSCoding协议,并且实现encodeWithCoder方法用来转化数据为二进制,实现initWithCoder实现二进制数据还原成类对象,OC的常见类,例如数组、字典等已经实现了这些内容,直接转换即可,如果是自己定义的类,需要手动实现。

    下面以将自定义的Person类转化为二进制存储,然后再读取出来的过程,来加深对这个功能的理解。

    【具体案例】

    ①定义Peron类,有三个属性,如下,注意要遵循NSCoding协议。

    #import <Foundation/Foundation.h>
    
    @interface Person : NSObject <NSCoding>
    
    @property (nonatomic, copy) NSString *name;
    @property (nonatomic, assign) NSInteger age;
    @property (nonatomic, assign) double height;
    
    @end
    ②实现编码和解码的方法,并且重写description方法方便打印类内数据。

    注意:encode和decode时要选择合适的数据类型

    #import "Person.h"
    
    @implementation Person
    
    - (void)encodeWithCoder:(NSCoder *)encoder{
        
        [encoder encodeObject:self.name forKey:@"name"];
        [encoder encodeInteger:self.age forKey:@"age"];
        [encoder encodeDouble:self.height forKey:@"height"];
        
    }
    
    - (id)initWithCoder:(NSCoder *)decoder{
        
        if (self = [super init]) {
            
            self.name = [decoder decodeObjectForKey:@"name"];
            self.age = [decoder decodeIntegerForKey:@"age"];
            self.height = [decoder decodeDoubleForKey:@"height"];
        }
        
        return self;
        
    }
    
    - (NSString *)description{
        
        return [NSString stringWithFormat:@"%@ %ld %lf",_name,_age,_height];
        
    }
    
    @end
    ③随机生成一些Person对象,使用NSKeyedArchiver进行二进制转换,然后存入文件,注意到因为对象放到了数组里,因此对象不需要主动转化为二进制,这个过程会自动完成,注意一定要实现上面的decode和encode方法

    NSMutableArray *persons = [NSMutableArray array];
    for (int i = 0; i < 100; i++) {
        Person *p = [[Person alloc] init];
        p.name = [NSString stringWithFormat:@"<%05d>",arc4random_uniform(10000)];
        p.age = arc4random_uniform(100);
        p.height = 1.5 + arc4random_uniform(60) / 100.0;
        [persons addObject:p];
    }
    [NSKeyedArchiver archiveRootObject:persons toFile:@"/Users/soulghost/Desktop/persons.data"];
    ④读取文件,使用NSKeydUnarchiver进行还原,在还原数组时,数组内的数据也被自动还原
    NSMutableArray *persons = [NSKeyedUnarchiver unarchiveObjectWithFile:@"/Users/soulghost/Desktop/persons.data"];
    NSLog(@"%@",persons);
    由于重写了description方法,类的内容会规范的打印如下:

        "<07060> 10 1.960000",
        "<05393> 35 1.960000",
        "<01438> 68 1.920000",
        "<00835> 40 1.710000",
        "<00035> 14 1.780000",
        "<08394> 66 1.910000",
        "<00504> 29 1.580000",
        "<03072> 4 1.900000",
        "<00473> 7 1.800000",
        "<04528> 10 1.790000",
        "<05930> 3 1.790000",
        "<07390> 2 1.590000",
        "<00820> 62 1.670000",
        ...

    通过这么一个简单的案例,就能学会任意对象和二进制对转的方法,这个方法能够跨越不同语言间的类定义不同而实现统一的数据存储,能够轻松实现类的数据库存储。

  • 相关阅读:
    onSaveInstanceState和onRestoreInstanceState()
    Android TextView中文字通过SpannableString来设置超链接、颜色、字体等属性
    又优化了一下 Android ListView 异步加载图片
    ListView异步加载图片
    SpannableString 设置一段文字中部分字体颜色
    Android Studio apk 打包流程
    svn分支开发与主干合并(branch & merge)
    SVN使用教程之——分支、合并
    XMPP协议实现原理介绍
    监听器
  • 原文地址:https://www.cnblogs.com/aiwz/p/6154064.html
Copyright © 2011-2022 走看看