一、概念 Core Data相当于封装了sqlite
1.Core Data 是数据持久化存储的最佳方式
2.数据最终的存储类型可以是:SQLite数据库,XML,二进制,内存里,或自定义数据类型
core Data存储的路径格式是URL类型
sqlite 存储的路径格式是 string类型
在Mac OS X 10.5Leopard及以后的版本中,开发者也可以通过继承NSPersistentStore类以创建自定义的存储格式
3.好处:能够合理管理内存,避免使用sql的麻烦,高效
4.构成:
(1)NSManagedObjectContext(被管理的数据上下文, 就是临时数据库 增删改查就是操作的临时DB)
操作实际内容(操作持久层)
作用:插入数据,查询数据,删除数据
(2)NSManagedObjectModel(被管理的数据模型, 比如Student)
数据库所有表格或数据结构,包含各实体的定义信息
作用:添加实体的属性,建立属性之间的关系
操作方法:视图编辑器,或代码
(3)NSPersistentStoreCoordinator(持久化存储助理)
相当于数据库的连接器
作用:设置数据存储的名字,位置,存储方式,和存储时机
(4)NSManagedObject(被管理的数据记录)
相当于数据库中的表格记录
(5)NSFetchRequest(获取数据的请求)
相当于查询语句
(6)NSEntityDescription(实体结构)
相当于表格结构
(7)后缀为.xcdatamodeld的包
里面是.xcdatamodel文件,用数据模型编辑器编辑
编译后为.momd或.mom文件
创建Core Data的步骤
创建单表步骤
1. cmd + shift + N 创建工程, 要勾选 Use Core Data
3. cmd + N 添加NSManagedObject subclass (被管理对象子类)
next 创建成对象
NSFetchRequest 描述搜索条件的一个实例用于从持久存储中检索数据。
NSEntityDescription 对象描述了一个实体的核心数据。实体管理对象类是什么id,或者使用一个数据库analogy-what表行。实例指定一个实体的名字,其属性(属性和关系,表达了NSAttributeDescription和NSRelationshipDescription)的实例和类的代表。
NSPredicate 类是用于定义逻辑条件用于限制搜索获取或者内存筛选
NSEntityDescription 对象描述了一个实体的核心数据。实体管理对象类是什么id,或者使用一个数据库analogy-what表行。实例指定一个实体的名字,其属性(属性和关系,表达了NSAttributeDescription和NSRelationshipDescription)的实例和类的代表。
NSPredicate 类是用于定义逻辑条件用于限制搜索获取或者内存筛选
示例代码
<span style="font-size:14px;">//
// ViewController.m
// CoreData-01
//
// Created by on 15/10/9.
// Copyright (c) 2015年 nieyinlong. All rights reserved.
//
#import "ViewController.h"
#import "AppDelegate.h" // 引入头文件 进行懒加载 NSManagedObjectContext
#import "Student.h" // 导入学生对象
@interface ViewController ()
#pragma mark---- 属性声明 被管理对象上下文(临时数据库)
@property (nonatomic, strong) NSManagedObjectContext *managerContext;
@end
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
}
#pragma mark--- 添加 (操作的是临时DB)
- (IBAction)addBtnAction:(id)sender {
//NSLog(@"添加");
// 1. 创建实体描述
// entityForName: 实体名
NSEntityDescription *studentDB = [NSEntityDescription entityForName:@"Student" inManagedObjectContext:self.managerContext];
// 循环添加实体 (也就是给临时数据库的学生数据表添加一条条信息)
for (int i = 0; i < 10; i++) {
// 2. 根据实体描述创建实体
Student *student = [[Student alloc] initWithEntity:studentDB insertIntoManagedObjectContext:self.managerContext];
// 3. 给实体赋值
student.name = [NSString stringWithFormat:@"军军%d号", i];
student.sex = [NSString stringWithFormat:@"男"];
student.age = [NSNumber numberWithInt:18 + i];
} // 循环结束就是添加了十条数据
// 添加单条数据
/*
// 2. 根据实体描述创建实体
Student *student = [[Student alloc] initWithEntity:studentDB insertIntoManagedObjectContext:self.managerContext];
// 3. 给实体赋值
student.name = [NSString stringWithFormat:@"军军1号"];
student.sex = [NSString stringWithFormat:@"男"];
student.age = [NSNumber numberWithInt:18];
*/
// 添加到临时数据库以后需要同步到file
NSError *error = nil;
[self.managerContext save:&error]; // 同步
if (!error) {
NSLog(@"存储成功");
}
}
#pragma mark--- 查询
- (IBAction)selectBtnAction:(UIButton *)sender {
// 用实体名 初始化一个 获取请求
NSFetchRequest *request = [[NSFetchRequest alloc] initWithEntityName:@"Student"];
// 创建实体描述
NSEntityDescription *studentDB = [NSEntityDescription entityForName:@"Student" inManagedObjectContext:self.managerContext];
// 给获取请求设置实体
request.entity = studentDB;
/**
* 数组接收查询的数据
* @param NSFetchRequest 请求
* @return 查询后的数组
*/
NSArray *array = [self.managerContext executeFetchRequest:request error:nil];
// 便利数组 (没有限定范围, 查询全部)
for (Student *stu in array) {
NSLog(@"查询全部: 姓名:%@, 年龄:%@, 性别:%@", stu.name, stu.age, stu.sex); // 打印结果是无序的
}
// 按年龄排序
// YES 代表升序 NO是降序
NSSortDescriptor *sort = [[NSSortDescriptor alloc] initWithKey:@"age" ascending:YES];
// 把排序好的数组放进 request.sortDescriptors
request.sortDescriptors = @[sort];
//------------------------------------------------------------------------------------
//-------- 开始按照谓词条件 查询 (限定范围) ---------------------------------------------------------
// 设置查询 根据指定条件查询 (相当于sql语句) // Predicate 代表陈述语句
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"name = %@", @"军军8号"];
// 查询包含 "8" 的 学生信息 (模糊查询)
// NSPredicate *predicate = [NSPredicate predicateWithFormat:@"name CONTAINS %@", @"8"];
// 查询后面的几个字符未知的信息 (模糊查询)
//NSPredicate *predicate = [NSPredicate predicateWithFormat:@"name LIKE %@", @"军军*"];
// 给请求加 陈述语句
request.predicate = predicate;
/*// 连写
request.predicate = [NSPredicate predicateWithFormat:@"name = %@", @"张三"];*/
// 利用设置好的请求条件取出临时数据库中的对应的数据
NSArray *preArray = [self.managerContext executeFetchRequest:request error:nil];
// 便利数组
for (Student *stu in preArray) {
NSLog(@"按谓词条件查询的结果: 姓名:%@, 年龄:%@, 性别:%@", stu.name, stu.age, stu.sex); // 打印结果是: 按谓词条件查询的结果: 姓名:军军8号, 年龄:26, 性别:男
}
// 数据同步
NSError *error = nil;
[self.managerContext save:&error];
if (!error) {
NSLog(@"查询成功");
}
}
#pragma mark--- 修改
- (IBAction)updateBtnAction:(UIButton *)sender {
// 用实体名 初始化一个 获取请求
NSFetchRequest *request = [[NSFetchRequest alloc] initWithEntityName:@"Student"];
// 创建实体描述
NSEntityDescription *studentDB = [NSEntityDescription entityForName:@"Student" inManagedObjectContext:self.managerContext];
// 给请求设置实体描述
request.entity = studentDB;
// 这里连写等效于以上两步
// request.entity = [NSEntityDescription entityForName:@"Student" inManagedObjectContext:self.managerContext];
// 设置谓词条件 (修改的限定范围是性别为男的学生)
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"sex = %@", @"男"];
request.predicate = predicate; // 把设置好的谓词条件赋值给 NSFetchRequest类的predicate属性
// 接收查询的数据 , 根据设置好的请求 查询临时数据库(上下文) , 此时的道的数组就是sex = 男的全部信息
NSArray *array = [self.managerContext executeFetchRequest:request error:nil];
// 遍历查询后的数据
for (Student *stu in array) {
stu.name = [NSString stringWithFormat:@"军军9999999号"]; // 把性别为男的 名字为"军军8号"的学生的姓名改为: "军军1000000号"
NSLog(@"修改后: %@, %@, %@", stu.name, stu.age, stu.sex);
}
NSError *error = nil;
[self.managerContext save:&error];
if (!error) {
NSLog(@"修改成功");
}
}
#pragma mark--- 删除
- (IBAction)delecteBtnAction:(UIButton *)sender {
// 请求
NSFetchRequest *request = [[NSFetchRequest alloc] initWithEntityName:@"Student"];
// 实体描述
NSEntityDescription *studentDB = [NSEntityDescription entityForName:@"Student" inManagedObjectContext:self.managerContext];
// 设置查询实体
request.entity = studentDB;
// 谓词条件 (限定要删除的条件)
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"name = %@", @"军军2号"];
request.predicate = predicate; // 给请求添加谓词条件
// 连写 等效于上面的两句
// request.predicate = [NSPredicate predicateWithFormat:@"name = %@", @"军军2号"];
/**
* 根据设置好的请求查找临时数据库 返回一个数组
* @param NSFetchRequest 请求
* @return 查询后的数组
*/
NSArray *array = [self.managerContext executeFetchRequest:request error:nil]; // 此时数组存储了name = 军军2号的数据
// 遍历查询后的数组
for (Student *stu in array) {
[self.managerContext deleteObject:stu]; // 删除 name = 军军2号 的那条数据
NSLog(@"%@%@%@", stu.name, stu.age, stu.sex);
}
// 同步
NSError *error = nil;
[self.managerContext save:&error];
if (!error) {
NSLog(@"删除成功");
}
}
#pragma mark---- 被管理对象上下文的懒加载方法
- (NSManagedObjectContext *)managerContext
{
if (!_managerContext) {
// 获取Appdelegate当中的被管理对象上下文(临时DB)
_managerContext = ((AppDelegate *)[UIApplication sharedApplication].delegate).managedObjectContext;
}
return _managerContext;
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
}
@end</span><span style="font-size: 24px;">
</span>