iOS面试题(1)

作者: T_aa | 来源:发表于2016-07-15 09:05 被阅读793次





    问题来源:

    http://www.zhihu.com/question/19604641/answer/56306604



    网上的一些答案:

    http://www.tuicool.com/articles/AVnMVj

    以下答案是个人理解,如果有问题欢迎指正。

    Model层:

    • 数据持久化存储方案有哪些?
    1.SQLite3
    2.Preference(偏好设置)
    3.Plist
    4.Coredata
    5.NSKeyedArchive(归档)
    
    • 沙盒的目录结构是怎样的?各自一般用于什么场合?



    参考:http://blog.csdn.net/iunion/article/details/46889073

    1.应用程序包:只读,不会被iTurns同步,存放应用程序本身包括资源文件和可执行文件等
    2.Document:会被iTurns同步,保存应用程序的数据文件,保存的是不可再生的数据
    3.Documents/Inbox:会被iTurns同步,保存其他应用程序请求当前当前程序打开的文件
    4.Library:会被iTurns同步,除了Caches,苹果建议用来存放默认设置和其他的状态信息
    5.Library/Caches:不会被iTurns同步,主要是缓存文件,用户使用过程中缓存的都可以保存在这个目录中,保存可再生文件,比如网络请求的数据。删除缓存文件一般会把这个文件删除
    6.Library/Preferences:会被iTurns同步,保存NSUserDefault的应用程序偏好配置信息文件,是一个plist文件
    7.tmp:不会被iTurns同步,存放临时文件,保存的是应用程序再次启动的时候不需要的文件,系统内存不足的时候就会去自动去清理他
    
    • SQL语句问题:inner join、left join、right join的区别是什么?
    left join(左联接) 返回包括左表中的所有记录和右表中联结字段相等的记录 
    right join(右联接) 返回包括右表中的所有记录和左表中联结字段相等的记录
    inner join(等值连接) 只返回两个表中联结字段相等的行
    <这块不是很懂>
    
    • sqlite的优化
    SQLite数据库文件读写操作,频繁打开关闭是很耗时和浪费资源,一些sql执行语句可以先缓存到内存中,然后依次性执行。
    数据排序
    查询语句的形式
    <这块不是很懂>
    
    • 网络通信用过哪些方式(100%的人说了AFNetworking...)
    TCP
    HTTP
    HTTPS
    UDP
    Socket
    
    用信号量,dispatch_semaphore_t
    
    • 在网络请求中如何提高性能
    1.减少请求带宽-JSON和XML是常见的请求与响应提的编码方式。压缩模式的效率在很大程序上取决于待压缩的数据,通常情况下JSON更高效
    2.降低请求延迟
    3.避免网络请求-利用缓存机制,缓存的内容就不要再次请求了
    <不是很懂>
    
    • 在网络请求中如何保证安全性


    参考:http://blog.csdn.net/jt521xlg/article/details/49717571

    1.用户post请求,不直接暴露参数信息
    2.重要的数据,要加密,常见的MD5(不可逆),AES(可逆)
    3.非重要的数据,要签名
    4.利用token校验时效性
    

    语言与基础知识:

    • 内存中的栈和堆的区别是什么?那些数据在栈上,哪些在堆上?
    栈:编译器自动分配释放,存放函数的参数值,局部变量的值
    堆:由程序猿管理释放,存放静态变量,字符常量,资源,编译运行时的数据
    
    • #defineconst定义的变量,有什么区别
    define:无类型校验、无分配内存、使用的话内存上多次拷贝、预处理的时候展开
    const:有类型校验、有分配内存、使用的话内存上一次拷贝、编译运行阶段使用
    
    
    • 什么情况下会出现内存的循环引用
    1.NSTimer-他的target是self的时候,要手动停止定时器
    2.Block-retain circle
    3.delegate
    
    • block中的weak self,是任何时候都需要加的么?
    调用自身属性的时候或者方法的时候
    
    • GCD的queue,main queue中执行的代码,一定是在main thread么?
    看:http://www.tuicool.com/articles/AVnMVj
    <不是很懂>
    
    • NSThread中的Runloop的作用,如何使用?
    <不知>
    
    • .h文件中的变量,外部可以直接访问么?(注意是变量,不是property)
    直接访问的话是没法访问到的,可以通过runtime的ivar去获取他的所有变量信息遍历就可以获取到
    
    • 讲述一下runtime的概念,message send如果寻找不到相应的对象,会如何进行后续处理 ?
    runtime是运行时语言,是系统运行时的机制,主要是消息机制。
    message_send找不到对应的方法的时候会执行resolveInstanceMethod,在里面可动态添加方法实现
    
    • TCP和UDP的区别是什么?
    TCP:传输控制协议、  有链接的、可靠的、
    UDP:用户数据报协议、无链接的、不可靠、
    
    • MD5和Base64的区别是什么,各自场景是什么?


    参考:http://www.cnblogs.com/XL-Sunny/p/5614012.html

    MD5:    不可逆、消息完整性保护。用于:1、一次性验证。2.安全访问认证。3、数字证书
    Base64: 可逆、是一种编码方式,主要作用不是加密,是用来避免‘字节’中不能转换成可显示字符的数值,将二进制数据转换成文本数据,方便使用HTTP协议等。使用场合:表示、传输、储存一些二进制数据。
    
    • 二叉搜索树的概念,时间复杂度多少?
    它获取是一个空树、或者是具有以下性质的二叉树:若他的左子树不空,则左子树上所有节点上的值均小于他根节点的值,若他的右子树不空,则右子树上所有节点的值均大于他根节点的值。
    <时间复杂度不知>
    

    架构:

    • 哪些类不适合使用单例模式?即使他们在周期中只会出现一次。
    单例是只有一个实例,并向整个系统提供这个实例。
    哪些类不适合<不知>
    
    • Notification的使用场景是什么?同步还是异步?
    Notification是事件广播机制,默认情况下,广播一个通知会阻塞后面的代码、直到所有的监听者都执行完响应、从这个上看广播是同步的。如果希望广播事件异步处理,可以将它加到新的线程中执行
    
    • 简单介绍一下KVC和KVO,他们都可以应用在哪些场景?
    
    KVO:键值监听、监听某个属性值变化
    
    KVC:键值编码、直接通过property的name(key)来访问这个property的属性。
    
    

    APP相关:

    • 如何添加一个自定义字体到工程中
    1.将自定义的字体拖到工程中
    2.在info的plsit文件中添加Fonts provided by application项,将新字体的名字添加进去,要带后缀.ttf
    
    • 如何制作一个静态库/动态库,他们的区别是什么?
    静态库:在编译的时候就会被链接到目标代码中,程序运行时候不再需要改静态库
    
    动态库:动态库在程序编译时并不会被链接到目标代码中,只有在程序运行时载入,因为程序运行期间还需要动态库存在
    
    我们封装的.a和.framework都是属于静态库。动态库苹果是不允许上商店。系统的framework基本上都是属于动态库。
    
    • Configuration中,debug和release的区别是什么?
    Debug:是调试版本,包含程序信息更多,只有debug程序才能断点、单步执行、调试语句输出
    
    Release:是发行版本,比debug有了一些优化,文件比debug的小,跟debug调用两个不同的底层库
    
    • 简单介绍下发送系统消息的机制(APNS)
    和本地通知不同,推送通知是通过苹果APNS发送到客户端
    1.应用设备向苹果APNS服务器注册推送服务
    2.注册成功之后APNS服务器会返回一个device_token,拿到这个token之后保存下来,到应用服务器后台
    3.需要推送服务的时候、应用服务器后台会将消息按指定的格式打包,然后结合device token一并发给APNS服务器
    4.然后APNS通过注册时候的device token将消息发送到注册的设备上
    

    UI:

    • 系统如何寻找到需要响应用户操作的那个Responder
    响应对象(Responder)-是具有响应和处理事件能力的对象,UIResponder是所有响应对象的基类。
    
    用户点击屏幕-》检测到触摸的事件将其打包成UIEvent对象,并放入当前活动的UIApplication事件队列中-》取出该事件交给UIWindow来处理-》window首先使用hitTest:withEvent寻找此次touch操作的初始点所在的视图view-》次方法会调用pointInside:withEvent判断点击点是否在视图内以确定是不是点击了当前视图-》如果点击的是当前的视图以此类推遍历这个视图的子视图-》直到找到这个touch操作所在的位置
    
    
    • 多屏幕尺寸的适配
    自动布局,使用Masonry
    
    • UIButton的父类是什么?UILabel呢?
    UIButton:父类 UIControl,UIControl的父类是UIView,多了一层,在UIControl中多了一些交互事件的处理。
    
    UILabel:父类 UIView
    
    
    • push view controller 和 present view controller的区别
    使用Push,必须要求当前的控制器在UINavigationController里面,present只要求当前是一个UIViewControler就行。
    push是基于当前逻辑操作上叠加一个新的控制器
    present一般是临时性的弹出一个界面
    
    
    • 描述下tableview cell的重用机制
    重用通过每个cell指定一个重用表示reuseIdentity,即指定单元格的种类,当cell滚出屏幕的时候,会将滚出屏幕的单元格放入重用的queue中,当某个未在屏幕上显示的单元格要显示的时候,就会从这个queue中取出进行重新,通过重用cell可以达到节省内存给的目的
    
    
    • UIView的frame和bounds的区别是什么
    frame是参照父视图的坐标系统
    
    bounds是本身的坐标系统。原点是(0,0)
    

    场景题

    • 发送10个网络请求,然后再接收到所有回应之后执行后续操作,如何实现?
    使用dispatch_group_t,开始一个任务enter,结束一个任务release,完成之后回调notify
    
    dispatch_group_t queueGroup = dispatch_group_create();
    
    dispatch_group_enter(queueGroup);
    
    dispatch_group_leave(queueGroup);
    
    dispatch_group_notify(queueGroup, dispatch_get_main_queue(), ^{
    
    });
    
    
    
    • 实现一个第三方控件,可以在任何时候出现在APP界面最上层
    1.将这个视图添加在Window上
    2.将这个控件做成一个新的window,显示在最上层
    
    • 实现一个最简单的点击拖拽功能。上面那个拖拽之外,如果在手放开时,需要根据速度往前滑动呢?
    给要拖拽的视图添加上UIPanGestureRecognizer手势,设置视图的center
    停止之后的减速利用velocityInView来获取停止时候的速度。
    代码:
    
    CGPoint velocity = [panGestureRecognizer velocityInView:self.view];
                
    CGFloat vMax = 3000;
    CGFloat distanceMax = 60;
    
    CGFloat finalDisX = (velocity.x * distanceMax)/vMax;
    CGFloat finalDisY = (velocity.y * distanceMax)/vMax;
    
    CGFloat finalDisXY = sqrtf((finalDisX * finalDisX) + (finalDisY* finalDisY));
    
    CGPoint finalPoint = CGPointMake(panGestureRecognizer.view.center.x + finalDisX, panGestureRecognizer.view.center.y + finalDisY);
    
    finalPoint.x = MIN(MAX(finalPoint.x, 0), self.view.bounds.size.width);
    
    finalPoint.y = MIN(MAX(finalPoint.y, 0), self.view.bounds.size.height);
    
    [UIView animateWithDuration:finalDisXY/distanceMax delay:0 options:UIViewAnimationOptionCurveEaseOut | UIViewAnimationOptionAllowUserInteraction animations:^{
        
        panGestureRecognizer.view.center = finalPoint;
        
    } completion:nil];
    
    • 如何减小一个应用程序的尺寸?
    1.资源图片压缩
    2.清理删除不必要的文件
    3.压缩视频音频
    4.解压ipa文件。查看哪个文件占用空间大,适当优化
    
    
    • 如何提高一个性用程序的性能?


    参考:http://blog.csdn.net/cuiweijie3/article/details/8987965

    1.ARC进行内存管理
    2.适当情况下使用reuseIdentity 重用
    3.尽可能将view设置为不透明(Opaque)
    4.避免臃肿的xib
    5.不要阻塞主线程
    6.让图片的大小UIimageview一样
    7.选择正确的合集-使用适合的类和对象编写代码
    8.使用GZip压缩-使用GZip对网络传输中的数据进行压缩,减小文件的大小,并加快下载的速度,压缩对文本的数据特别有用,文本具有很高的压缩比,NSURLConnection默认已经支持GZip压缩
    
    9.重用和延迟加载view
    10.缓存
    11.考虑绘制
    12.处理内存警告
    13.重用花销很大的对象
    14.使用Sprite Sheets-游戏
    15.避免重新处理数据
    16.选择正确的数据格式
    17.设置适当的背景图片
    18.降低web内容的影响
    19.设置阴影路径
    20.优化tableview
    21.选择正确的数据储存方式
    
    22.加速启动时间
    23.使用Autorelease pool-临时对象不使用的时候,自动释放
    24.缓存图片或不缓存-imageNamed加载图片的时候这个图片是有缓存下来,使用imageWithContentOfFile是没有缓存,如果经常使用到的则缓存下来比较合适
    25.尽量避免Date格式化
    
    • 不同版本的APP,数据库结构变化了,如何处理?
    新建一个新的数据库,旧的数据库数据导出来,按新的数据库的结构存入新的数据库中。
    

    相关文章

      网友评论

        本文标题:iOS面试题(1)

        本文链接:https://www.haomeiwen.com/subject/hleejttx.html