iOS面试题(6-10)

0D6829F1A95EA9C1B42E3FD9413D5230.jpg

6.UIView与CALayer有什么区别

UIView管理绘制与事件处理(尤其是触摸事件).CALayer完全关乎绘制.事实上,UIView依靠CALayer来管理绘制.CALayer不处理用户的交互
每个UIView都有一个CALayer用于绘制.而且每个CALayer都可以拥有子图层

7.iOS怎么做数据的持久化

沙箱目录

iOS应用程序只能访问自己的目录,这个目录称为沙箱目录,应用程序间禁止数据的共享和访问

1>Documents目录:用于存储非常大的文件或需要频繁更新的数据,能够进行iTunes或iCloud备份.

// documentDirectory是只有一个元素的数组
NSArray *documentDirectory = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);

NSString *myDocPath = [documentDirectory objectAtIndex:0];
或
NSString *myDocPath = [documentDirectory lastObject];

2>Library目录:下有Preferences(用于存放应用程序的设置数据)和Caches目录(存储缓存文件)

3>tmp目录:临时文件目录,用户可以访问它.不能进行iTunes和iCloud的备份

NSString *tmpDirectory = NSTemporaryDirectory();

持久化方式:属性列表,对象归档,SQLite数据库,Core Data

属性列表:集合对象可以读写到属性列表文件中

iOS面试题(6-10)_第1张图片
屏幕快照 2016-07-30 下午6.40.43.png

NSArray类的方法(NSDictionary的方法类似):

  • arrayWithContentsOfFile
  • initWithContentOfFile
  • writeToFile:atomically 该方法把NSArray对象写入到属性列表文件中,第一个参数是文件名,第二个参数为是否使用辅助文件,如果为YES,则先写入一个辅助文件,然后辅助文件再重新命名为目标文件,如果为NO,则直接写入到目标文件


    iOS面试题(6-10)_第2张图片
    屏幕快照 2016-07-30 下午7.07.12.png
// NoteDAO.h
#import 
#import "Note.h"

@interface NoteDAO : NSObject

+ (NoteDAO *)sharedManager;

- (NSString *)applicationDocumentsDirectoryFile;

- (void)createEditableCopyOfDatabaseIfNeeded;

// 插入备忘录的方法
- (int)create:(Note *)model;

// 删除备忘录的方法
- (int)remove:(Note *)model;

// 修改备忘录的方法
- (int)modify:(Note *)model;

// 查询所有数据方法
- (NSMutableArray *)findAll;

// 按照主键查询数据方法
- (Note *)findById:(Note *)model;

@end
// NoteDAO.m

#import "NoteDAO.h"

@implementation NoteDAO

static NoteDAO *sharedManager = nil;

- (void)createEditableCopyOfDatabaseIfNeeded {
    NSFileManager *fileManager = [NSFileManager defaultManager];
    NSString *writableDBPath = [self applicationDocumentsDirectoryFile];
    
    BOOL dbexits = [fileManager fileExistsAtPath:writableDBPath];
    if (!dbexits) {
        NSString *defaultDBPath = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:@"NotesList.plist"];
        NSError *error;
        BOOL success = [fileManager copyItemAtPath:defaultDBPath toPath:writableDBPath error:&error];
        if (!success) {
            NSAssert1(0, @"错误写入文件:'%@'.", [error localizedDescription]);
        }
    }
}

- (NSString *)applicationDocumentsDirectoryFile {
    NSString *documentDirectory = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    NSString *path = [documentDirectory stringByAppendingPathComponent:@"NotesList.plist"];
    return path;
}

+ (NoteDAO *)sharedManager {
    static dispatch_once_t once;
    dispatch_once(&once, ^{
        sharedManager = [[self alloc] init];
        [sharedManager createEditableCopyOfDatabaseIfNeeded];
    });
    return sharedManager;
}

- (int)create:(Note *)model {
    NSString *path = [self applicationDocumentsDirectoryFile];
    NSMutableArray *array = [[NSMutableArray alloc] initWithContentsOfFile:path];
    
    NSDateFormatter *dateFormat = [[NSDateFormatter alloc] init];
    [dateFormat setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
    
    NSDictionary *dict = [NSDictionary dictionaryWithObjects:@[[dateFormat stringFromDate:model.date], model.content] forKeys:@[@"date", @"content"]];
    [array addObject:dict];
    [array writeToFile:path atomically:YES];
    
    return 0;
}

- (int)remove:(Note *)model {
    NSString *path = [self applicationDocumentsDirectoryFile];
    NSMutableArray *array = [[NSMutableArray alloc] initWithContentsOfFile:path];
    
    for (NSDictionary *dict in array) {
        NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
        [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];

        NSDate *date = [dateFormatter dateFromString:[dict objectForKey:@"date"]];
        
        // 比较日期主键是否相等
        if ([date isEqualToDate:model.date]) {
            [array removeObject:dict];
            [array writeToFile:path atomically:YES];
            break;
        }
    }
    return 0;
}

- (int)modify:(Note *)model {
    NSString *path = [self applicationDocumentsDirectoryFile];
    NSMutableArray *array = [[NSMutableArray alloc] initWithContentsOfFile:path];
    
    for (NSDictionary *dict in array) {
        NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
        [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
        
        NSDate *date = [dateFormatter dateFromString:[dict objectForKey:@"date"]];
        NSString *content = [dict objectForKey:@"content"];
        
        if ([date isEqualToDate:model.date]) {
            [dict setValue:content forKey:@"content"];
            [array writeToFile:path atomically:YES];
            break;
        }
    }
    return 0;
}

- (NSMutableArray *)findAll {
    NSString *path = [self applicationDocumentsDirectoryFile];
    
    NSMutableArray *listData = [[NSMutableArray alloc] init];
    
    NSMutableArray *array = [[NSMutableArray alloc] initWithContentsOfFile:path];
    for (NSDictionary *dict in array) {
        NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
        [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
        
        Note *note = [[Note alloc] init];
        note.date = [dateFormatter dateFromString:[dict objectForKey:@"date"]];
        note.content = [dict objectForKey:@"content"];
        
        [listData addObject:note];
    }
    return listData;
}

- (Note *)findById:(Note *)model {
    NSString *path = [self applicationDocumentsDirectoryFile];
    NSMutableArray *array = [[NSMutableArray alloc] initWithContentsOfFile:path];
    
    for (NSDictionary *dict in array) {
        NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
        [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
        
        Note *note = [[Note alloc] init];
        note.date = [dateFormatter dateFromString:[dict objectForKey:@"date"]];
        note.content = [dict objectForKey:@"content"];
        
        if ([note.date isEqualToDate:model.date]) {
            return note;
        }
    }
    return nil;
}

@end

对象归档:对象归档是一种序列化方式,首先将归档对象序列化为一个文件,然后在通过反归档将数据恢复到对象中.但是不适用于大量数据和频繁读写的情况.

使用要求:该对象的类必须实现NSCoding协议,而且每个成员变量应该是基本数据类型或都是实现NSCoding协议的某个类的实例

// NoteDAO_Archive.h
#import 
#import "Note.h"

// 归档文件名
#define FILE_NAME @"NotesList.archive"
// 归档数据的键
#define ARCHIVE_KEY @"NotesList"

@interface NoteDAO_Archive : NSObject
+ (NoteDAO_Archive *)sharedManager;

- (NSString *)applicationDocumentsDirectoryFile;

- (void)createEditableCopyOfDatabaseIfNeeded;

// 插入备忘录的方法
- (int)create:(Note *)model;

// 删除备忘录的方法
- (int)remove:(Note *)model;

// 修改备忘录的方法
- (int)modify:(Note *)model;

// 查询所有数据方法
- (NSMutableArray *)findAll;

// 按照主键查询数据方法
- (Note *)findById:(Note *)model;
@end
// NoteDAO_Archive.m
#import "NoteDAO_Archive.h"

@implementation NoteDAO_Archive
static NoteDAO_Archive *sharedManager = nil;

- (void)createEditableCopyOfDatabaseIfNeeded {
    NSFileManager *fileManager = [NSFileManager defaultManager];
    NSString *writableDBPath = [self applicationDocumentsDirectoryFile];
    
    BOOL dbexits = [fileManager fileExistsAtPath:writableDBPath];
    if (!dbexits) {
        NSString *path = [self applicationDocumentsDirectoryFile];
        
        NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
        [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
        
        NSDate *date1 = [dateFormatter dateFromString:@"2010-08-04 16:01:03"];
        Note *note1 = [[Note alloc] init];
        note1.date = date1;
        note1.content = @"Welcome to MyNotes.";
        
        NSDate *date2 = [dateFormatter dateFromString:@"2011-12-04 16:01:03"];
        Note *note2 = [[Note alloc] init];
        note2.date = date2;
        note2.content = @"欢迎使用MyNotes.";
        
        NSMutableArray *array = [[NSMutableArray alloc] init];
        [array addObject:note1];
        [array addObject:note2];
        
        NSMutableData *theData = [NSMutableData data];
        NSKeyedArchiver *archiver = [[NSKeyedArchiver alloc] initForWritingWithMutableData:theData];
        // 归档数据是放置在NSArray对象中的,将NSArray对象进行归档,NSArray对象内部没哟个元素都是Note对象,而Note对象也必须是能够被归档的,所以Note类实现了NSCoding协议
        [archiver encodeObject:array forKey:ARCHIVE_KEY];
        [archiver finishEncoding];
        
        [theData writeToFile:path atomically:YES];
    }
}

- (NSString *)applicationDocumentsDirectoryFile {
    NSString *documentDirectory = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    NSString *path = [documentDirectory stringByAppendingPathComponent:@"NotesList.plist"];
    return path;
}

+ (NoteDAO_Archive *)sharedManager {
    static dispatch_once_t once;
    dispatch_once(&once, ^{
        sharedManager = [[self alloc] init];
        [sharedManager createEditableCopyOfDatabaseIfNeeded];
    });
    return sharedManager;
}

- (int)create:(Note *)model {
    NSString *path = [self applicationDocumentsDirectoryFile];
 
    NSMutableArray *array = [self findAll];
    [array addObject:model];
    
    /**
     *  首先实例化NSMutableData对象theData
     *  然后把theData作为参数,再实例化NSKeyedArchiver对象archiver
     *  archiver对象的encodeObject:方法可以键对实现NSCoding协议的对象进行归档
     *  [archiver finishEncoding]发出归档完成消息
     */
    
    NSMutableData *theData = [NSMutableData data];
    NSKeyedArchiver *archiver = [[NSKeyedArchiver alloc] initForWritingWithMutableData:theData];
    [archiver encodeObject:array forKey:ARCHIVE_KEY];
    [archiver finishEncoding];
    [theData writeToFile:path atomically:YES];
    
    return 0;
}

- (int)remove:(Note *)model {
    NSString *path = [self applicationDocumentsDirectoryFile];
    NSMutableArray *array = [self findAll];
    
    for (Note *note in array) {
        // 比较日期主键是否相等
        if ([note.date isEqualToDate:model.date]) {
            [array removeObject:note];
            NSMutableData *theData = [NSMutableData data];
            NSKeyedArchiver *archiver = [[NSKeyedArchiver alloc] initForWritingWithMutableData:theData];
            [archiver encodeObject:array forKey:ARCHIVE_KEY];
            [archiver finishEncoding];
            [theData writeToFile:path atomically:YES];
            break;
        }
    }
    return 0;
}

- (int)modify:(Note *)model {
    NSString *path = [self applicationDocumentsDirectoryFile];
    NSMutableArray *array = [self findAll];
    
    for (Note *note in array) {
        // 比较日期主键是否相等
        if ([note.date isEqualToDate:model.date]) {
            note.content = model.content;
            NSMutableData *theData = [NSMutableData data];
            NSKeyedArchiver *archiver = [[NSKeyedArchiver alloc] initForWritingWithMutableData:theData];
            [archiver encodeObject:array forKey:ARCHIVE_KEY];
            [archiver finishEncoding];
            [theData writeToFile:path atomically:YES];
            break;
        }
    }
    return 0;
}

- (NSMutableArray *)findAll {
    NSString *path = [self applicationDocumentsDirectoryFile];
    
    NSMutableArray *listData = [[NSMutableArray alloc] init];
    NSData *theData = [NSData dataWithContentsOfFile:path];
    
    if (theData.length > 0) {
        NSKeyedUnarchiver *archiver = [[NSKeyedUnarchiver alloc] initForReadingWithData:theData];
        listData = [archiver decodeObjectForKey:ARCHIVE_KEY];
        [archiver finishDecoding];
    }
    
    return listData;
}

- (Note *)findById:(Note *)model {
    NSString *path = [self applicationDocumentsDirectoryFile];
    NSMutableArray *listData = [[NSMutableArray alloc] init];
    NSData *theData = [NSData dataWithContentsOfFile:path];
    
    if (theData.length > 0) {
        NSKeyedUnarchiver *archiver = [[NSKeyedUnarchiver alloc] initForReadingWithData:theData];
        listData = [archiver decodeObjectForKey:ARCHIVE_KEY];
        [archiver finishDecoding];
        
        for (Note *note in listData) {
            // 比较日期主键是否相等
            if ([note.date isEqualToDate:model.date]) {
                return note;
            }
        }
    }
    return nil;
}
@end

SQLite数据库:关系数据库SQLite采用C语言编写,具有可移植性强,可靠性高,小而容易使用的特点.

运行时与它的应用程序之间共用相同的进程空间,而不是单独的两个进程.支持多表,索引,事务,视图和触发是无数据类型的数据库.
虽然SQLite可以忽略数据类型,但从编程规范上讲,应该在Create Table语句中指定数据类型
INTEGER 有符号的整数类型
REAL 浮点类型
TEXT 字符串类型
BLOB 二进制大对象类型,能够存放任何二进制数据

// NoteDAO_SQLite.h
#import 
#import "Note.h"
#import "sqlite3.h"

#define DBFILE_NAME @"NotesList.sqlite3"

@interface NoteDAO_SQLite : NSObject
{
    sqlite3 *db;
}

+ (NoteDAO_SQLite *)sharedManager;

- (NSString *)applicationDocumentsDirectoryFile;

- (void)createEditableCopyOfDatabaseIfNeeded;

// 插入备忘录的方法
- (int)create:(Note *)model;

// 删除备忘录的方法
- (int)remove:(Note *)model;

// 修改备忘录的方法
- (int)modify:(Note *)model;

// 查询所有数据方法
- (NSMutableArray *)findAll;

// 按照主键查询数据方法
- (Note *)findById:(Note *)model;
@end

// NoteDAO_SQLite.m
#import "NoteDAO_SQLite.h"

@implementation NoteDAO_SQLite
static NoteDAO_SQLite *sharedManager = nil;

- (void)createEditableCopyOfDatabaseIfNeeded {
    NSString *writableDBPath = [self applicationDocumentsDirectoryFile];
    
    if (sqlite3_open([writableDBPath UTF8String], &db) != SQLITE_OK) {
        sqlite3_close(db);
        NSAssert(NO, @"数据库打开失败");
    } else {
        char *err;
        NSString *createSQL = [NSString stringWithFormat:@"create table if not exists Note (cdate text primary key, content text);"];
        if (sqlite3_exec(db, [createSQL UTF8String], NULL, NULL, &err) != SQLITE_OK) {
            sqlite3_close(db);
            NSAssert1(NO, @"建表失败, %s", err);
        }
        sqlite3_close(db);
    }
}

- (NSString *)applicationDocumentsDirectoryFile {
    NSString *documentDirectory = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
    NSString *path = [documentDirectory stringByAppendingPathComponent:@"NotesList.plist"];
    return path;
}

+ (NoteDAO_SQLite *)sharedManager {
    static dispatch_once_t once;
    dispatch_once(&once, ^{
        sharedManager = [[self alloc] init];
        [sharedManager createEditableCopyOfDatabaseIfNeeded];
    });
    return sharedManager;
}

- (int)create:(Note *)model {
    NSString *path = [self applicationDocumentsDirectoryFile];
    
    if (sqlite3_open([path UTF8String], &db) != SQLITE_OK) {
        sqlite3_close(db);
        NSAssert(NO, @"数据库打开失败");
    } else {
        NSString *sqlStr = @"insert or replace into note (cdate,content) values (?,?)";
        
        sqlite3_stmt *statement;
        // 预处理过程
        if (sqlite3_prepare_v2(db, [sqlStr UTF8String], -1, &statement, NULL) == SQLITE_OK) {
            NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
            [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
            NSString *nsdate = [dateFormatter stringFromDate:model.date];
            
            // 绑定参数开始
            sqlite3_bind_text(statement, 1, [nsdate UTF8String], -1, NULL);
            sqlite3_bind_text(statement, 2, [model.content UTF8String], -1, NULL);
            
            // 执行插入
            if (sqlite3_step(statement) != SQLITE_OK) {
                NSAssert(NO, @"插入数据失败");
            }
        }
        sqlite3_finalize(statement);
        sqlite3_close(db);
    }
    
    return 0;
}

- (int)remove:(Note *)model {
    NSString *path = [self applicationDocumentsDirectoryFile];
    
    if (sqlite3_open([path UTF8String], &db) != SQLITE_OK) {
        sqlite3_close(db);
        NSAssert(NO, @"数据库打开失败");
    } else {
        NSString *sqlStr = @"delete from note where cdate = ?";
        sqlite3_stmt *statement;
        // 预处理过程
        if (sqlite3_prepare_v2(db, [sqlStr UTF8String], -1, &statement, NULL) == SQLITE_OK) {
            NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
            [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
            NSString *nsdate = [dateFormatter stringFromDate:model.date];
            
            // 绑定参数开始
            sqlite3_bind_text(statement, 1, [nsdate UTF8String], -1, NULL);
            // 执行插入
            if (sqlite3_step(statement) != SQLITE_DONE) {
                NSAssert(NO, @"删除数据失败");
            }
        }
        sqlite3_finalize(statement);
        sqlite3_close(db);
    }

    return 0;
}

- (int)modify:(Note *)model {
    NSString *path = [self applicationDocumentsDirectoryFile];
    
    if (sqlite3_open([path UTF8String], &db) != SQLITE_OK) {
        sqlite3_close(db);
        NSAssert(NO, @"数据库打开失败");
    } else {
        NSString *sqlStr = @"update note set content=? where cdate = ?";
        sqlite3_stmt *statement;
        // 预处理过程
        if (sqlite3_prepare_v2(db, [sqlStr UTF8String], -1, &statement, NULL) == SQLITE_OK) {
            NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
            [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
            NSString *nsdate = [dateFormatter stringFromDate:model.date];
            
            // 绑定参数开始
            sqlite3_bind_text(statement, 1, [model.content UTF8String], -1, NULL);
            sqlite3_bind_text(statement, 2, [nsdate UTF8String], -1, NULL);
            // 执行插入
            if (sqlite3_step(statement) != SQLITE_DONE) {
                NSAssert(NO, @"修改数据失败");
            }
        }
        sqlite3_finalize(statement);
        sqlite3_close(db);
    }
    
    return 0;
}

- (NSMutableArray *)findAll {
    NSString *path = [self applicationDocumentsDirectoryFile];
    NSMutableArray *listData = [[NSMutableArray alloc] init];
    
    if (sqlite3_open([path UTF8String], &db) != SQLITE_OK) {
        sqlite3_close(db);
        NSAssert(NO, @"数据库打开失败");
    } else {
        NSString *qsql = @"select cdate,content from Note";
        
        sqlite3_stmt *statement;
        // 预处理过程
        if (sqlite3_prepare_v2(db, [qsql UTF8String], -1, &statement, NULL) == SQLITE_OK) {
            NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
            [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
            
            while (sqlite3_step(statement) == SQLITE_ROW) {
                char *cdate = (char *)sqlite3_column_text(statement, 0);
                NSString *nscdate = [[NSString alloc] initWithUTF8String:cdate];
                
                char *content = (char *)sqlite3_column_text(statement, 1);
                NSString *nscontent = [[NSString alloc] initWithUTF8String:content];
                
                Note *note = [[Note alloc] init];
                note.date = [dateFormatter dateFromString:nscdate];
                note.content = nscontent;
                [listData addObject:note];
            }
        }
        sqlite3_finalize(statement);
        sqlite3_close(db);
    }
    return listData;
}

- (Note *)findById:(Note *)model {
    NSString *path = [self applicationDocumentsDirectoryFile];
    
    if (sqlite3_open([path UTF8String], &db) != SQLITE_OK) {
        sqlite3_close(db);
        NSAssert(NO, @"数据库打开失败");
    } else {
        NSString *qsql = @"select cdate,content from Note where cdate = ?";
        
        sqlite3_stmt *statement;

        
        // 预处理过程,将SQL编译成二进制代码,提高SQL语句的执行速度
        if (sqlite3_prepare_v2(db, [qsql UTF8String], -1, &statement, NULL) == SQLITE_OK) {
            // 准备参数
            NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
            [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
            NSString *nsdate = [dateFormatter stringFromDate:model.date];
            // 绑定参数开始
            sqlite3_bind_text(statement, 1, [nsdate UTF8String], -1, NULL);
            
            // 执行
            if (sqlite3_step(statement) == SQLITE_ROW) {
                char *cdate = (char *)sqlite3_column_text(statement, 0);
                NSString *nscdate = [[NSString alloc] initWithUTF8String:cdate];
                
                char *content = (char *)sqlite3_column_text(statement, 1);
                NSString *nscontent = [[NSString alloc] initWithUTF8String:content];
                
                Note *note = [[Note alloc] init];
                note.date = [dateFormatter dateFromString:nscdate];
                note.content = nscontent;
                
                sqlite3_finalize(statement);
                sqlite3_close(db);
                return note;
            }
        }
        sqlite3_finalize(statement);
        sqlite3_close(db);
    }
    return nil;
}
@end

Core Data:苹果为Mac OS X和iOS系统应用开发提供的数据持久化技术.基于高级数据持久化API,底层最终是SQLite数据库,二进制文件和内存数据保存.

Core Data是一种ORM技术(对象关系映射


iOS面试题(6-10)_第3张图片
屏幕快照 2016-08-06 下午7.02.47.png

)
被管理对象上下文类(Managed Object Context, MOC)类,在上下文中可以查找,删除和插入对象,然后通过栈同步到持久化对象存储
被管理对象模型(Manaaged Object Model, MOM)类,是系统中的"实体",与数据库中的表等对象对应
持久化存储协调器(Persistent Store Coordinator, PSC)类,在持久化对象存储之上提供了一个接口,可以把它考虑成为数据库的连接
MOC,MOM,PSC和持久化对象存储,它们一起构成了Core Data堆栈
持久化对象存储(Persistent Object Store, POS)执行所有底层的从对象到数据的转换,并负责打开和关闭数据文件.它有3种持久化实现方式:SQLite,二进制文件和内存形式


iOS面试题(6-10)_第4张图片
屏幕快照 2016-08-06 下午7.17.37.png

10.BAD_ACCESS在什么情况下出现?

在访问一个已经释放的对象或向它发送消息时,EXC_BAD_ACCESS就会出现.造成EXC_BAD_ACCESS最常见的原因是,在初始化方法中初始化变量时用错了所有权修饰符,这会导致对象被释放.
例:在viewDidLoad方法中为UITableViewController创建了一个包含元素的NSMutableArray,却将该数组的所有权修饰符设成了unsafe_unretained或assign而不是strong.现在在cellForRowAtIndexPath:中,若要访问已经释放掉的对象时,就会得到名为EXC_BAD_ACCESS的崩溃.
通过设置NSZombieEnabled环境变量,来调试EXC_BAD_ACCESS

你可能感兴趣的:(iOS面试题(6-10))