iOS 沙盒機制及資料儲存等操作

zhf_Zachariah發表於2018-01-25

iOS的APP可以在自己的沙盒裡讀寫檔案,但是不可以訪問其他APP的沙盒。每一個APP都是一個資訊孤立的房間,這些房間就相當於一個沙盒,相互是不可以進行通訊的,唯獨可以通過URL Scheme。沙盒裡面的檔案可以是照片、聲音檔案、檔案、屬性列表等。

沙盒的根目錄結構:DocumentLibrarytemp。 1.Document:用於儲存使用者資料,iTunes備份和恢復的時候會包括此目錄。所以。蘋果建議將程式中建立的或在程式中瀏覽到的檔案資料儲存在該目錄下。 2.Library:包含兩個子目錄:CachesPreferencesCaches用來存放使用者需要換成的檔案。Preferences是APP的偏好設定,可以通過NSUserDefaults來讀取和設定。 3.tmp:用於存放臨時檔案,這個可以存放一些當APP退出後不需要再儲存的檔案。

######獲取沙盒路徑 //獲取路徑三種方法 NSString *path = NSHomeDirectory(); //拼接字串 NSString *documents = [path stringByAppendingString:@"/Documents"]; //專業拼接路徑 NSString *str = [path stringByAppendingPathComponent:@"Documents"]; ######系統提供的方法獲取Document路徑 NSArray *array = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES); NSString *strD = [array objectAtIndex:0]; NSLog(@"%@",strD); ######獲取library路徑 NSArray *arrayL = NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES); NSString *strL = [arrayL objectAtIndex:0]; NSLog(@"%@",strL); ######獲取tmp路徑 NSString *path = NSTemporaryDirectory(); NSLog(@"%@",path); ######獲取caches路徑 NSArray *arrayC = NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES); NSString *strC = [arrayC objectAtIndex:0]; NSLog(@"%@",strC); ######用NSUserDefaults對Preferences進行讀取和設定 NSUserDefaults *user = [NSUserDefaults standardUserDefaults]; [user setObject:@"zhangsan" forKey:@"name"]; [user setObject:@"lisi" forKey:@"names"]; //將資料同步到沙盒的規定目錄下(library下的preferences目錄) [user synchronize];

###基本型別資料的儲存和讀取

  • 字串儲存、讀取
- (void)saveString{
    //獲取Document目錄
    NSString *string = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    //在沙盒檔案下建立檔案
    NSString *newPath = [string stringByAppendingString:@"/text.txt"];
    //要存入的內容
    NSString *name = @"UMR";
    //寫入檔案
    [name writeToFile:newPath atomically:YES encoding:NSUTF8StringEncoding error:nil];
}
- (void)readingString{
    //獲取路徑
    NSString *str = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    NSString *newPath = [str stringByAppendingString:@"/text.txt"];
    //讀取資料
    NSString *string = [NSString stringWithContentsOfFile:newPath encoding:NSUTF8StringEncoding error:nil];
    NSLog(@"%@",string);
}
複製程式碼
  • 陣列儲存、讀取
- (void)saveArray{
    //1.獲取路徑
    //獲取目錄
    NSString *string = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    //在沙盒檔案下建立檔案
    NSString *newPath = [string stringByAppendingString:@"/array.plist"];
    //要存入的內容
    NSArray *array = @[@"zhangsan",@"lisi",@"wangwu"];
    //寫入
    [array writeToFile:newPath atomically:YES];
    NSLog(@"%@",newPath);
}
- (void)readingArray{
    //獲取路徑
    NSString *str = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    NSString *newPath = [str stringByAppendingString:@"/array.plist"];
    //讀取資料
    NSArray *array = [NSArray arrayWithContentsOfFile:newPath];
    NSLog(@"%@",array);
}
複製程式碼
  • 字典儲存、讀取
- (void)saveDictionary{
    //獲取路徑
    NSString *string = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    NSString *newPath = [string stringByAppendingString:@"/dictionary.plist"];
    //儲存內容
    NSDictionary *dict = @{@"n1":@[@"1",@"2",@"3"],@"n2":@{@"a":@"d",@"s":@"g"},@"n3":@"uuummmrrr"};
    [dict writeToFile:newPath atomically:YES];
    NSLog(@"%@",newPath);
}
- (void)readingDictionary{
    //獲取路徑
    NSString *string = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    NSString *newPath = [string stringByAppendingString:@"/dictionary.plist"];
    //讀取內容
    NSDictionary *dic = [NSDictionary dictionaryWithContentsOfFile:newPath];
    NSLog(@"%@",dic);
}
複製程式碼
  • data儲存、讀取
- (void)saveData{
    //獲取路徑
    NSString *string = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    //儲存路徑
    NSString *newPath = [string stringByAppendingString:@"/data.plist"];
    //儲存內容
    NSString *str = @"UMR";
    //將string轉換成data
    NSData *data = [str dataUsingEncoding:NSUTF8StringEncoding];
    //寫入資料夾
    [data writeToFile:newPath atomically:YES];
    NSLog(@"%@",newPath);
}
- (void)readingData{
    //獲取路徑
    NSString *string = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    //儲存路徑
    NSString *newPath = [string stringByAppendingString:@"/data.plist"];
    //從檔案讀取data
    NSData *data = [NSData dataWithContentsOfFile:newPath];
    //將data轉換成為string
    NSString *str = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
    NSLog(@"%@",str);
}
複製程式碼
  • image儲存 - 需轉換為data進行儲存和讀取
- (void)saveImage{
    //獲取路徑
    NSString *path = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    //在檔案路徑下面建立該資料夾
    NSString *newPath = [path stringByAppendingString:@"/image.png"];
    //將.png轉為data格式
    NSData *imageData = UIImagePNGRepresentation([UIImage imageNamed:@"name6.png"]);
//    NSData *imageD = UIImageJPEGRepresentation([UIImage imageNamed:@"name6.png"], 1); 如果是JPG格式的,後面的CGFloat為壓縮係數;
    //將data檔案寫入資料夾
    [imageData writeToFile:newPath atomically:YES];
    NSLog(@"%@",newPath);
}
- (void)readingImage{
    //獲取路徑,獲取檔案
    NSString *path = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    NSString *newPath = [path stringByAppendingString:@"/image.png"];
    NSData *imageData = [NSData dataWithContentsOfFile:newPath];
    //將data轉為圖片格式
    UIImage *image = [UIImage imageWithData:imageData];
    //獲取 - 賦值
    UIImageView *imageView = [[UIImageView alloc] initWithFrame:CGRectMake(120, 120, 120, 120)];
    imageView.image = image;
    [self.view addSubview:imageView];
    NSLog(@"%@",newPath);
}
複製程式碼

###歸檔與反歸檔 - 複雜資料的沙盒儲存

  • eg:先建立一個Person物件,宣告相關屬性
//歸檔必須遵守NSCoding協議
@interface Person : NSObject<NSCoding>
@property (nonatomic,strong) NSString *name;
@property (nonatomic,strong) NSString *gender;
@property (nonatomic,assign) NSInteger age;
@end```
 - 在.m檔案中實現這兩個NSCoding協議方法
複製程式碼

@implementation Person //對物件進行歸檔的時候呼叫

  • (void)encodeWithCoder:(NSCoder *)aCoder{ [aCoder encodeObject:self.name forKey:@"name"]; [aCoder encodeObject:self.gender forKey:@"gender"]; [aCoder encodeInteger:self.age forKey:@"age"]; } //對物件進行反歸檔的時候呼叫
  • (instancetype)initWithCoder:(NSCoder *)aDecoder{ if (self = [super init]) { self.name = [aDecoder decodeObjectForKey:@"name"]; self.gender = [aDecoder decodeObjectForKey:@"gender"]; self.age = [aDecoder decodeIntegerForKey:@"age"]; } return self; } @end```
  • 歸檔
- (void)saveData{
    Person *person = [[Person alloc] init];
    person.name = @"umr";
    person.gender = @"m";
    person.age = 18;
    //進行規檔操作
    //1.建立一個NSMutableData來儲存歸檔後的資料
    NSMutableData *Data = [[NSMutableData alloc] init];
    //2.建立歸檔器
    NSKeyedArchiver *archiver = [[NSKeyedArchiver alloc] initForWritingWithMutableData:Data];
    //3.進行歸檔
    [archiver encodeObject:person forKey:@"person"];
    //4.歸檔結束
    [archiver finishEncoding];
    //獲取沙盒路徑
    NSString *SDPath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    NSString *newPath = [SDPath stringByAppendingString:@"/archiver.plist"];
    //寫入檔案
    [Data writeToFile:newPath atomically:YES];
    NSLog(@"%@",newPath);
}```
 - 反歸檔
複製程式碼
  • (void)readData{ //獲取沙盒路徑 NSString *path = [[self documentPath] stringByAppendingString:@"/archiver.plist"]; //獲取資料 NSData *data = [NSData dataWithContentsOfFile:path]; NSKeyedUnarchiver *Unarchiver = [[NSKeyedUnarchiver alloc] initForReadingWithData:data]; Person *person1 = [Unarchiver decodeObjectForKey:@"person"]; [Unarchiver finishDecoding]; NSLog(@"%@ %ld %@",person1.name,person1.age,person1.gender); }```
- (NSString *)documentPath{
    return [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
}```
### - 物件陣列的歸檔與反歸檔
複製程式碼
  • (void)codeArray{ //建立兩個person物件 Person *person1 = [[Person alloc] init]; person1.name = @"huahua"; Person *person2 = [[Person alloc] init]; person2.name = @"UMR"; #存入陣列 - 陣列中的複雜物件必須遵守NSCoding協議,就可以直接對陣列進行歸檔 NSMutableArray *array = [[NSMutableArray alloc] initWithObjects:person1,person2, nil]; //獲取路徑 NSString *documentPath = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)[0]; NSString *path = [documentPath stringByAppendingPathComponent:@"array.plist"]; NSLog(@"%@",path); //歸檔 [NSKeyedArchiver archiveRootObject:array toFile:path]; //反歸檔 NSArray *arr = [NSKeyedUnarchiver unarchiveObjectWithFile:path]; // Person *per = arr[0]; NSLog(@"%@",arr); }```

相關文章