- 当页面跳转的时候,如何实现导航条和页面同时出现?因为他两个经常出现不同步的现象?
- 如何将tablview强制转换成UIScrollow?
- 当一个界面在6s上正好可以完全呈现,那在4s上面你是如何处理的?
- 说说你对MVC结构模式的理解,并说说它的优缺点?
- 说说商品使用倒计时抢购的思路?
- 如果两个页面的布局大致相同,只有少部分不一致,你是如何快速布局的?
- ARC下内存是否存在泄漏?举个实例.
- 在Model中给你两组数据.例如:一组为:name,age;另一组为:name,age,hight;你如何实现两组数据同时解析并且方便,快捷?
- 你平时写程序时,代码需要兼容到系统几?
- 你平时写程序时,NSTimer做过什么处理?
- 你对多线程理解吗?多线程之间是如何进行链接的?
- 使用过demo吗?详细阐述你自己最拿手的demo内容实现的原理或者机制?
- 当你引用一个瀑布流的第三方库时,发现有的版本上能够实现,有的版本上不能实现,你该做如何处理?
- svn的使用?
- 客户端一些比较私密的东西,你是如何进行保存的?保存在什么地方?
- 你们UI测试,一般测试你们项目的那些方面?举例有你们项目中比较具有代表性的bug?
- 支付的加密方式?
- 编译链接
- synthesize 和denamic的区别
@property有两个对应的词,一个是@synthesize,一个是@dynamic。如果@synthesize和@dynamic都没写,那么默认的就是@syntheszie var = _var;
@synthesize的语义是如果你没有手动实现setter方法和getter方法,那么编译器会自动为你加上这两个方法。
@dynamic告诉编译器,属性的setter与getter方法由用户自己实现,不自动生成。(当然对于readonly的属性只需提供getter即可)。假如一个属性被声明为@dynamic var,然后你没有提供@setter方法和@getter方法,编译的时候没问题,但是当程序运行到instance.var =someVar,由于缺setter方法会导致程序崩溃;或者当运行到 someVar = var时,由于缺getter方法同样会导致崩溃。编译时没问题,运行时才执行相应的方法,这就是所谓的动态绑定。
- 在项目开发中常用的开发工具有哪些?
- UITableView & UICollection
- NSProxy & NSObject
- Object & Swift
- 传值通知 & 推送通知(本地&远程)
- 第三方库 & 第三方平台
- NSCache & NSDcitionary
- UIView的setNeedsDisplay和setNeedsLayout方法
- UILayer & UIView
每一个UIView都包含一个CALayer对象,CALayer中存储的是UIView的展示内容数据,负责绘制.UIView管理CALayer,相当于一个管理者,并具备处理触摸事件的能力(因为uiview继承自uiresponder)
- layoutSubViews & drawRects
- UDID & UUID
- CPU & GPU
- 点(pt)& 像素(px)
px:像素
pt:独立像素 / point / 点
iOS 开发中用到的单位 pt 是独立像素的意思,它是绝对长度,不随屏幕像素密度变化而变化(和我们日常用到的毫米、厘米是一个意思,只是它要小得多),在非视网膜的 iPhone 上(iPhone 3G),苹果规定 1px=1pt,也就是说 pt 和像素点是一一对应的。但随着 iPhone 4 的到来,高分屏出现了(视网膜屏),这个时候 1pt 对应 2px。所以用固定长度 pt 作为开发单位的好处是:这样可以统一图形在同一种类不同型号设备上图形的大小。而如果用像素作为单位的话,就乱了套了,因为在不同像素密度的屏幕里面,像素本身大小是不一样的。
设备 屏幕类型 屏幕尺寸 点 分辨率(像素)
iphone 3GS 非Retina 3.5 320*480 320*480
iphone 4/4S Retina 3.5 320*480 640*960
iphone 5/5S/5C Retina 4 320*568 640*1136
iphone 6 Retina 4.7 375*667 750*1334
iphone 6 Plus Retina 5.5 414*736 1242*2208
总结:1.在Retina屏幕下一个点表示2像素,在非Retina屏幕下一个点表示1像素;
2.在iphone 6 Plus下一个点表示3个像素;
3.iOS 中的 pt 和安卓中的单位 dp 本质上是一个概念,都是独立像素的意思,只是叫法不一样而已
- 属性与成员变量
- int和NSInteger的区别
- import和include
#include与#import的区别:#include与#import其效果相同,只是后者不会引起重复导入,确保头文件只会导入一次;
#import与@class的区别:import是导入头文件,会把头文件的所有信息获取到,这个类有那些变量和方法.而@Class只会告诉编译器,其后面声明的名称是类的名称,至于这些类是如何定义的,完全不知道,所以即使在头文件中使用了@Class,还是需要在.m中导入头文件
注意:使用@Class是为了防止头文件之间相互导入.
- @class
见36答案
- 全局 & 静态变量
- 类和对象
- 分类拓展协议中哪些可以声明属性?
- 继承和类别的区别
- 分类的作用
- 分类的局限性
- category & extension
- NSArray和NSDictionary
- iOS遍历数组/字典的方法
- NSValue NSNumber
- 如何避免循环引用
- Core Foundation中提供了哪几种操作Socket的方法?
- 解析XML文件有哪几种方式?
- 什么是沙盒模型?哪些操作是属于私有api范畴?
- 在一个对象的方法里面:self.name= “object”;和 name =”object” 有什么不同吗?
- 请简要说明viewDidLoad和viewDidUnload何时调用
- 创建控制器、视图的方式
- 简述内存分区情况
- 队列和栈有什么区别
- 控件主要响应3种事件
- 简述视图控件器的生命周期
- app 项目的生命周期
- 应用的生命周期
- 简要说明一下APP的启动过程,main文件说起,main函数中有什么函数?作用是什么?
- UIApplicationMain函数作用
- main函数作用
- 动画有基本类型有哪几种;表视图有哪几种基本样式
- 实现简单的表格显示需要设置UITableView的什么属性、实现什么协议?
- Cocoa Touch提供了哪几种Core Animation过渡类型?
- UIView与CLayer有什么区别?
- Quatrz 2D的绘图功能的三个核心概念是什么并简述其作用
- iPhone OS主要提供了几种播放音频的方法?
- 使用AVAudioPlayer类调用哪个框架、使用步骤?
- 有哪几种手势通知方法、写清楚方法名?
系统提供了七种手势帮我们进行手势的识别开发:点击UITapGesture,滑动UIPanGestureRecognizer,轻扫UISwipeGestureRecognizer,旋转UIRotationGestureRecognizer,缩放UIPinchGestureRecognizer,长按UILocalizedIndexedCollation,屏幕边缘滑动UIScreenEdgePanGestureRecognizer;
- ViewController的didReceiveMemoryWarning怎么被调用
- 什么时候用delegate,什么时候用Notification?
- 用预处理指令#define声明一个常数,用以表明1年中有多少秒(忽略闰年问题
- 写一个”标准"宏MIN ,这个宏输入两个参数并返回较小的一个。
- 关键字const有什么含意?修饰类呢?static的作用,用于类呢?还有extern c的作用
- 关键字volatile有什么含意?并给出三个不同的例子
- 一个参数既可以是const还可以是volatile吗? 一个指针可以是volatile 吗?解释为什么。
- static 关键字的作用
- 列举几种进程的同步机制,并比较其优缺点。
- 进程之间通信的途径
- 进程死锁的原因
- 死锁的4个必要条件
〈1〉互斥条件。即某个资源在一段时间内只能由一个进程占有,不能同时被两个或两个以上的进程占有。这种独占资源如CD-ROM驱动器,打印机等等,必须在占有该资源的进程主动释放它之后,其它进程才能占有该资源。这是由资源本身的属性所决定的。如独木桥就是一种独占资源,两方的人不能同时过桥。
〈2〉不可抢占条件。进程所获得的资源在未使用完毕之前,资源申请者不能强行地从资源占有者手中夺取资源,而只能由该资源的占有者进程自行释放。如过独木桥的人不能强迫对方后退,也不能非法地将对方推下桥,必须是桥上的人自己过桥后空出桥面(即主动释放占有资源),对方的人才能过桥。
〈3〉占有且申请条件。进程至少已经占有一个资源,但又申请新的资源;由于该资源已被另外进程占有,此时该进程阻塞;但是,它在等待新资源之时,仍继续占用已占有的资源。还以过独木桥为例,甲乙两人在桥上相遇。甲走过一段桥面(即占有了一些资源),还需要走其余的桥面(申请新的资源),但那部分桥面被乙占有(乙走过一段桥面)。甲过不去,前进不能,又不后退;乙也处于同样的状况。
〈4〉循环等待条件。存在一个进程等待序列{P1,P2,...,Pn},其中P1等待P2所占有的某一资源,P2等待P3所占有的某一源,......,而Pn等待P1所占有的的某一资源,形成一个进程循环等待环。就像前面的过独木桥问题,甲等待乙占有的桥面,而乙又等待甲占有的桥面,从而彼此循环等待。
- 死锁的处理
- 自动释放池是什么,如何工作
- sprintf,strcpy,memcpy使用上有什么要注意的地方
- 你了解svn,cvs等版本控制工具么?
- 什么是push
- 静态链接库
- OC三大特性
- OC中如何实现多态
- oc中可修改和不可以修改类型
- 我们说的oc是动态运行时语言是什么意思?
- 通知和协议的不同之处?
- 做过的项目是否涉及网络访问功能,使用什么对象完成网络功能?
- 简单介绍下NSURLConnection类及+sendSynchronousRequest:returningResponse:error:与– initWithRequest:delegate:两个方法的区别?
- 谈谈Object-C的内存管理方式及过程?
- Object-C有私有方法吗?私有变量呢?
- 说说响应链
- 时间传递 & 响应者链
响应者链表示一系列的响应者对象.事件被交由第一响应者对象处理,如果第一响应者不处理,事件被沿着响应者链向上传递,交给下一个响应者.一般来说,第一响应者是个视图对象或者其子类对象,当其被触摸后事件被交由其他处理,如果不处理,事件就会被传递给它的视图控制器对象(如果不存在).如果是他的父视图(superview)对象(如果存在),以此类推,直到顶层视图.接下来会沿着顶层(top View)到窗口(UIWindow对象)再到程序(UIApplication对象).如果整个过程都没有响应这个事件,该事件就被丢弃.一般情况下,在响应者链中只要由对象处理事件,事件就停止传递.但有时候可以在试图的响应方法中根据一些判断条件来决定是否需要继续传递事件
常用UIView的下一个响应者是它的superview,但是当UIView是UIViewController的根试图的时候,它的下一个响应者就是UIViewController.UIViewController的下一个响应者是其根视图的superview.依次类推,直到UIWindow.UIWindow不处理UIApplication传递给APPDelegate,也不处理,事件就抛弃不再处理,只要有一个响应者处理事件,事件就不再传递
- frame和bounds有什么不同?
- 方法和选择器有何不同?
- OC的垃圾回收机制?
- 什么是延迟加载?
- 是否在一个视图控制器中嵌入两个tableview控制器?
- 一个tableView是否可以关联两个不同的数据源?你会怎么处理?
- 什么时候使用NSMutableArray,什么时候使用NSArray?
- 给出委托方法的实例,并且说出UITableVIew的Data Source方法
- 在应用中可以创建多少autorelease对象,是否有限制?
- 如果我们不创建内存池,是否有内存池提供给我们?
- 什么时候需要在程序中创建内存池?
- 类NSObject的那些方法经常被使用?
- 什么是简便构造方法?
- UIView的动画效果有那些?
- Object-C有多继承吗?没有的话用什么代替?cocoa 中所有的类都是NSObject 的子类
- 内存管理 Autorelease、retain、copy、assign的set方法和含义?
- C和obj-c 如何混用
实现文件的扩展名.m改成.mm即可,但cpp文件必须只能使用c/c++代码,而且cpp文件include的头文件中,也不能出现obj-c的代码,因为cpp只能写C++的代码.
- 类别的作用?继承和类别在实现中有何区别?
- 深拷贝与前拷贝区别
- 什么是深拷贝浅拷贝
- 字符串什么时候使用copy,strong
- 字符串所在内存区域
- mutablecopy和copy @property(copy) NSMutableArray *arr;这样写有什么问题
- 如何让自定义类可以使用copy修饰符
- 对于语句NSString*obj = [[NSData alloc] init]; obj在编译时和运行时分别时什么类型的对象?
- #import 跟#include 又什么区别,@class呢, #import<> 跟 #import”"又什么区别?
#include与#import的区别:#include与#import其效果相同,只是后者不会引起重复导入,确保头文件只会导入一次;
#import与@class的区别:import是导入头文件,会把头文件的所有信息获取到,这个类有那些变量和方法.而@Class只会告诉编译器,其后面声明的名称是类的名称,至于这些类是如何定义的,完全不知道,所以即使在头文件中使用了@Class,还是需要在.m中导入头文件
注意:使用@Class是为了防止头文件之间相互导入.
- 写一个setter方法用于完成@property (nonatomic,retain)NSString *name,写一个setter方法用于完成@property(nonatomic,copy)NSString *name
- 常见的Objective-C的数据类型有那些, 和C的基本数据类型有什么区别?如:NSInteger和int
- id 声明的对象有什么特性?
- 原子(atomic)跟非原子(non-atomic)属性有什么区别?
nonatomic:非原子性,就是多线程访问的时候不加锁,允许多线程同时修改属性的值;
atomic:原子性,就是防止在未完成的时候被另外一个线程读取,造成数据错误.
- 如何对iOS设备进行性能测试?
- 设计模式
全局只需要一个对象,可以存储到单例类的属性中,这样每个类都可以方便的访问同一份数据.(比如全局的设置类,用户的登录信息);
一个对象的创建比较消耗资源.
- mvvm模式
- 观察者模式(通知,KVO)
代理是一对一,通知是一对多;
代理可以相互传值,通知只能单向传值.发通知的对象给接收通知的对象传值;
通知的效率低于代理(想一想为什么,通知是需要查询所有注册者的信息的,符合接收条件,才调用对象的方法,代理是直接对象调用方法.回顾通知和代理的原理,你就懂了).
代理有有线(有线网络)的,通知是无线(wifi)的.
- 工厂模式
工厂模式解决的问题是多态,一个类可能有多个子类,具体需要那个子类,工厂根据不同的条件返回不同的子类对象.在IOS中类簇就是工厂模式.(使用类簇的类,NSString,NSNumber,NSArray等).
- 代理模式
解决类和类之间的事件,传递性.把一个类中发生的事件通知到另一个类中,使用代理模式可以降低类和类之间的耦合度;
delegate使用assign是防止delegate和self产生循环引用;
- 策略模式
- 适配器模式
- 模版模式
- 外观模式
- 创建模式
- MVP模式
- 说说常用的几种传值方式
- 对于单例的理解
- KVO,NSNotification,delegate及block区别
- 什么是runtime
runtime相当于OC转换成C的代码,可以实现许多OC实现不了的功能或者比较麻烦的功能.例如:为类别添加属性;
只需要回答,系统内部是靠objc_msgSend来现实方法调用的所有的oc方法的调用都会编译为objc_msgSend方法
- runtime干什么用,使用场景
runtime相当于OC转换成C的代码,可以实现许多OC实现不了的功能或者比较麻烦的功能.例如:为类别添加属性;
只需要回答,系统内部是靠objc_msgSend来现实方法调用的所有的oc方法的调用都会编译为objc_msgSend方法
- 使用bugly进行崩溃分析
- KVO & KVC
KVC
可以修改只读属性和私有变量的值;
Key value Coding是cocoa的一个标准组成部分,他能让我们可以通过name(key)的方法访问property,不必调用明确的property accesser(set/get方法).
KVC是一个用于间接访问对象属性的机制(一种使用字符串而不是访问器方法去访问一个对象实例变量的机制).使用该机制不需要调用set或者get方法以及来访问成员变量,它通过setValue:forkey和valueForkey:方法.
KVC的机制是啥样的呢?他是以字符串的形式向对象发送消息字符串是要关注属性的关键.是否存在setter,getter方法.如果不存在,他将在内部查找名为_key或key的实例变量,如果没有会调用setValueForUndefindedKey:如果也没有,则会运行报错;注意是如果是基本数据类型,则需要封装一下(NSNumber)
KVC的使用环境:
无论是property还是普通的全局属性变量,都可以用KVC
KVC的优缺点:
优点:主要的好处就是减少代码量;没有property的变量也能通过KVC来设置;
缺点:如果key写错时,编译不会报错,运行的时候才会报错.
KVO的理解:
KVO是一个对象能够观察另外一个对象的属性值,并且能够发现值的变化.KVO更加适合任何类型的对象倾听另外一个任意对象的改变,或者是一个对象与另外一个对象保持同步的一种方法,即当另外一种对象的状态发生改变时,观察对象马上作出反应.他只能用来对属性做出反应,而不会用来对方法或者动作做出反应
KVO的优点:
能够提供一种简单的方法实现两个对象间的同步;
能够对非我们创建的对象,即内部对象的状态改变作出响应,而且不需要改变内部对象的现实;
能够获得观察的属性的属性的最新值以及先前值;
用key path来观察属性,因此也可以观察嵌套对象(也就是可以观察一个对象内部对象的属性的变化,可以无限嵌套)观察,前提是对象的属性支持KVO);
完成了对观察对象的抽象,因为不需要额外的代码来允许观察值能够被观察(不需要像通知一样还需要发送通知,KVO属性的改变,外部可以直接观察).
KVO的注意事项:
我们注册KVO的时候,要观察那个属性,在调用注册方法的时候,addObserver:forKey:options:context:forKey处填写的属性是以字符串形式,万一属性名字写错,因为是字符串,编译器也不会出现警告以及检查
KVO的使用:
被观察者发出addObserver:forKey:options:context:方法来添加观察者,然后只要被观察者的keyPath的值变化(注意:单纯改变其值不会调用次方法,只有通过getters和setters来改变值才会触发KVO),就会在观察者里调用方法observerValueForKeyPath:ofObject:change:context:因此观察者需要实现方法observerValueForKeyPath:ofObject:change:context:来对KVO发出的通知作出响应;
这些代码只需要在观察者里进行实现,被观察者不用添加任何代码,所以谁要监听谁注册,然后对响应进行处理即可,使得观察者与被观察者完全解藕,运用很灵活很简单;但是KVO只能检测类中的属性,并且属性名是通过NSSTring来查找,编译器不会帮你查错和补全,纯手敲所以比较容易出错
- NSThread,NSOperationQueue和GCD的区别是什么
NSThread:
相当于自己创建一个线程,创建线程的时候,可以把一个方法放到创建的线程中.
优点:NSThread比其他两个轻量级;
缺点:需要自己管理线程的生命周期,线程同步,线程同步时对数据的加锁会有一定的系统开销.
NSOperation
NSOperation不需要自己创建线程,只关注需要在线程中完成的代码,然后把NSOperation放到NSOperationQueue中即可,NSOperationQueue会把代码放到分线程中执行.
NSOperation的作用:配合使用NSOperation和NSOperationQueue也能实现多线程编程.
NSOperation和NSOperationQueue实现多线程的具体步骤:
先需要执行的操作封装到一个NSOperation对象中的main方法;
然后将NSOperation对象添加到NSOperationQueue中;
系统会自动将NSOperationQueue中的NSOperation取出来;
将取出的NSOperation封装的操作放到一个新线程中执行;
NSOperation的子类:
NSOperation是一个抽象类,并不具备操作的能力,必须使用它的子类;
使用NSOperation子类的方式有3种:
NSInvocation;在主线程中创建方法,则在主线程中执行;在分线程中创建方法,则在分线程中执行;
NSBlockOperation;会自动查找空闲的线程进行使用;
自定义类继承NSOperation,实现内部相应的方法;NSOperation默认是在主线程中开启的.重写main方法,把子类对象放入NSOperationQueue中,就会自动在分线程执行main方法了.
附加:
AFNetworking和SDWebimage都是使用来实现异步的;
当多个线程同时修改一个变量的值的时候,需要加锁,防止混乱.
优点:不需要关心线程管理,数据同步的事情,可以把精力放在自己需要执行的操作上.
GCD
GCD是苹果公司开发的技术,以优化的应用程序支持多核心处理器和其他的对称多处理系统的系统.这建立在任务进行执行的线程池模式的基础上的;
GCD的队列是怎么使用的?通过同步或异步的方式把任务提交到队列中;
GCD的工作原理:
让程序平行排队的特定任务,根据可用的处理资源,安排他们在任何可用的处理器核心上执行任务;
一个任务可以是一个函数或者是一个block.GCD的底层依然是线程实现,不过这样可以让程序员不用关注实现的细节;
GCD中必须要使用的是各种队列,我们通过block,把具体的代码放到队列中,队列中的任务排队执行,系统会自动的把队列中的各个任务分配到具体的线程中和cpu中,具体创建多少个线程,分配到哪个cpu上,都是由系统管理
GCD中有三种队列类型:
The main queue:系统自带的一个队列,放到这个队列中的代码会被系统分配到主线程中执行.main queue可以调用dispath_main_queue()来获得.因为main queue是与主线程相关的,所以这是一个串行队列,提交至其中的任务顺序执行(一个任务执行完毕以后,在执行下一个任务);
Global queues:整个应用程序存在三个全局队列(系统已经创建好,只需要获得即可):高,中(默认),低三个优先级队列.可以调用dispatch_get_global_queue函数传入优先级来访问队列.全局队列是并行队列,可以让多个任务并发(同时)执行(自动开启多个线程r同时执行任务)并发功能只有在异步函数下有效;
用户自己创建队列:dispatch_queue_create创建的队列,可以是串行的,也可以是并行的,因为系统已经给我们提供了并行,串行队列,所以一般情况下我们不再需要再创建自己的队列.用户创建的队列可以有任意多个
注意:分线程中不能刷新UI,刷新UI只能在主线程.如果每个线程都可以刷新UI,将会很容易造成UI冲突,会出现不同步的情况,所以只有主线程中能刷新UI系统是为了降低编程的复杂度,最大程度的避免冲突
分线程中回到主线程只要有两种方式:
performSeletorOnMainThread;
使用main queue;
分线程在使用的时候,有以下几个需要说明的地方
之前的版本中分线程不会自动创建autorelease pool,所以需要在分线程创建autorelease pool,目前SDK版本已经不需要了;
如果多个线程修改(只是读取变量,不会有问题)同一个资源,需要注意线程同步的问题
timer不能在分线程中直接使用,需要手动开启run loop
附加:
同步:等待提交的任务执行完毕,才继续执行当前任务;
异步:不等待提交的任务执行完毕,继续执行当前任务;
为什么需要线程?一个线程只能执行一个任务,任务耗时较长,那么后边的任务都处于等待状态,所以需要把耗时较长的任务放入到分线程执行;
多线程是并发执行的;
同步不会产生新的线程;
异步可能会产生新的线程;
同步提交到主线程会造成或死锁现象,在主线程中执行同步的方式提交任务且阻塞主线程.
- 进程和线程的区别与联系是什么?
- 别异步执行两个耗时操作,等两次耗时操作都执行完毕后,再回到主线程执行操作. 使用队列组(dispatch_group_t)快速,高效的实现上述需求
- 在项目什么时候选择使用GCD,什么时候选择NSOperation?
- 串行队列同步执行和异步主队列
- dispatch_barrier_async的作用是什么?
- +(void)load与 +(void)initialize区别load 和 initialize方法的区别
- 说说关于UDP/TCP的区别
tcp和udp都是网络传输层的协议,tcp提供可靠的数据连接,udp提供不可靠的数据连接,不会对数据包的顺序,是否丢失进行校验,如果丢失也不会重新发送,但是tcp会验证数据包的顺序,丢失还会重新发送,所以是可靠的.但是udp得优点正是因为少了这些校验,及时性更好一些,所以常见的视频聊天,音频聊天都是用的是udp协议,即使丢失一两个包,也无妨,最多声音模糊一下或者画面稍微卡顿
TCP是面向连接的,一对一的通信,UDP是广播方式,一对多的方式.我们使用socket的时候,可以选择使用tcp或者udp.
CP有三次握手,UDP没有,TCP连接的三次握手:
第一次握手:客户端发送syn包到服务器,并进入SYN_SEND状态,等待服务器确认;
第二次握手:服务器收到syn包,必须确认客户的SYN,同时自己也发送一个syn包,即SYN+ACK包,此时服务器进入SYN+RECV状态;
第三次握手:客户端到服务器的SYN+ACK包,向服务器发送确认包ACK,此时发送完毕,客户端和服务器进入established状态,完成三次握手.完成三次握手后,客户端和服务器之间开始传输数据.
- http和scoket通信的区别?socket连接相关库,TCP,UDP的连接方法,HTTP的几种常用方式?
- block
- 使用block时什么情况会发生引用循环,如何解决?
- 在block内如何修改block外部变量?
- Block & MRC-Block
- 什么是block
- block 实现原理
- 关于block
- 使用block和使用delegate完成委托模式有什么优点
- 多线程与block
- 谈谈对Block 的理解?并写出一个使用Block执行UIVew动画?
- Weak、strong、copy、assign 使用
- 什么情况使用 weak 关键字,相比 assign 有什么不同?
- 怎么用 copy 关键字?
- weak & strong
strong是强引用,weak是弱引用,强引用指向的对象不会被释放;
强引用指向的对象不会被释放;
弱引用不会对对象的引用计数产生影响;
一个对象没有被强引用会立刻释放,弱引用指向的对象在释放时会自动置空.
- 这个写法会出什么问题: @property (copy) NSMutableArray *array
- 如何让自己的类用 copy 修饰符?如何重写带 copy 关键字的 setter?
- @property 的本质是什么?ivar、getter、setter 是如何生成并添加到这个类中的
- ivar、getter、setter 是如何生成并添加到这个类中的?
- 用@property声明的NSString(或NSArray,NSDictionary)经常使用copy关键字,为什么?如果改用strong关键字,可能造成什么问题?
- @protocol 和 category 中如何使用 @property
- runtime如何通过selector找到对应的IMP地址?
- retain和copy区别
- copy和strong的使用?
- NSString和NSMutableString,前者线程安全,后者线程不安全
- readwrite,readonly,assign,retain,copy,weak ,strong,nonatomic 属性的作用
- UITableView
- UITableView最核心的思想
- 定义高度
- 自定义高度原理
- 老生常谈之UITableView的性能优化
- cell高度的计算
- 定高的cell和动态高度的cell
- TableView渲染
- 减少视图的数目
- 减少多余的绘制操作
- 不要给cell动态添加subView
- 异步化UI,不要阻塞主线程
- 滑动时按需加载对应的内容
- 离屏渲染的问题
- 离屏渲染优化方案
- 数据存储
一共四中方式,属性列表(通过WriteToFile 或者userDefault(偏好设置)存入到Plist文件),对象序列化(归档和解档),SQLite数据库,CoreData;
所有的本地持久化数据存储的本质都是写文件,而且只能存到沙盒中;
盒机制:就是苹果的一项安全机制,本质就是系统给每个应用分配了一个文件夹来存储数据,而且每个应用只能访问分配给自己的那个文件夹,其他应用的文件夹是不能访问的;
沙盒中默认有三个文件夹,其中Library文件夹中包括两个子文件,分别是Caches和Preferences文件夹:
Documents:存储用户相关的数据,用来存放不会被清理的数据.(用户拍摄的视频,用户创作的图片,用户唱的歌曲,用户收藏的商品),可以在当中添加子文件夹,iTunes备份和恢复的时候,会包括此目录。
Library/Caches目录:存放缓存文件,iTunes不会备份此目录,此目录下文件不会在应用退出删除。一般存放体积比较大,不是特别重要的资源。
Library/Preferences目录:保存应用的所有偏好设置(偏好设置也就是userDefault),ios的Settings(设置)应用会在该目录中查找应用的设置信息,iTunes会自动备份该目录
tmp:放临时文件,不需要永久存储的,比如下载的时候,需要存储到临时文件中,最终拷贝到Documents或者Library中,iphone重启后会清空tmp目录
属性列表:
userDefault(偏好设置)存储7中数据类型:数组,字典,字符串.NSData,NSDate,NSNumber和Boolean;默认会存在沙盒Library 中的Preference文件夹中一个以bundleIdentifier命名的plist(property list 属性列表)文件中.不需要自己再去创建路径
应用于存储少量的数据,比如登录的用户信息,应用程序配置信息等.只有数组,字典,字符串,NSData, Boolean可以通过WriteToFile(图片类型在存储的时候需要先转化为NSData类型)进行存储;依旧是存储在Plist文件;
Plist文件中可以存储的7中数据类型:数组,字典,字符串.NSData,NSDate,NSNumber和Boolean.
对象序列化(也叫做归档):
对象序列化最终也是存为属性列表文件,如果程序中,需要存储的时候,直接存储对象比较方便.例如有一个设置类,我们可以把这个设置类的对象直接存储,就没有必要再把里面的每一个属性单独存到文件中.对象序列化是将一个实现了NSCoding协议的对象,通过序列化(NSKeydArchiver)的形式,将对象中的属性抽取出来,转化为二进制,也就是NSData,可是NSData可以通过另外一种方式就是write to file方式或者存储到NSUserdefault中.要想使用对象序列化就必须要实现的两个方法:endcodeWithCoder,initWithCoder.对象序列化的本质就是对象NSData
对象序列化的本质就是将对象类型转化为二进制数据类型;
对象反序列化的本质就是将二进制数据NSData转化为对象.
SQLite(也叫关系性数据库):
适合大量,重复,有规律的数据存储.而且频繁的读取,删除,过滤数据.我们通常使用FMDB第三方
CoreData(对象关系映射):
其实就是把对象的属性和表中的字段自动映射,简化程序员的负担,以面向对象的方式操作数据库.
CoreData本质还是数据库,只不过使用起来更加面向对象,不关注二维的表结构,而是只需要关注对象,纯面向对象的数据操作方式.我们直接使用数据库的时候,如果向数据库中插入数据,一般是把一个对象的属性和数据库中某个表的字段一一对应,然后把对象的属性存储到具体的表字段中.取一条数据的时候,把表中的一行数据取出,同样需要在封装到对象的属性中,这样的方式有点繁琐,不面向对象.CoreData解决的问题就是不需要这个中间的转化过程,看起来是直接把对象存储进去,并且取出,不关心表的存在,实际内部做好了映射关系.
- Objective-C堆和栈的区别?
- 内存管理
堆(heap),栈(stack)
alloc,new,copy的对象创建在堆上面的,需要我们自己负责管理,若程序员不释放,则内存就会溢出.栈内存一般是由系统自己创建并管理的,例如方法内的指针,形式参数等,系统会把这些变量放到栈中,并在方法结束的时候自动释放掉.
- iOS内存区域
- 字符串的内存管理
- 你是如何优化内存管理
- 循环引用
- autorelease的使用
- 工厂方法为什么不释放对象
- ARC下autorelease的使用场景
- 自动释放池如何工作
- 避免内存峰值
- ARC和MRC的混用
- NSTimer的内存管理
- ARC的实现原理
大家可以把经历过的在评论区回复,我帮忙进行汇整